Merge pull request #4615 from influxdata/flux/show-errors

Show errors instead of 'No Results' when error occurs
remember-threesizer
Iris Scholten 2018-10-19 10:17:32 -07:00 committed by GitHub
commit 5eba55af1e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 55 additions and 10 deletions

View File

@ -51,6 +51,7 @@ export const getAST = async (request: ASTRequest) => {
export interface GetRawTimeSeriesResult { export interface GetRawTimeSeriesResult {
didTruncate: boolean didTruncate: boolean
csv: string csv: string
ok: boolean
uuid?: string uuid?: string
} }
@ -74,15 +75,17 @@ export const getRawTimeSeries = async (
) )
try { try {
const {body, byteLength, uuid: responseUUID} = await manager.fetchFluxData( const {
url, body,
renderedScript, byteLength,
uuid ok,
) uuid: responseUUID,
} = await manager.fetchFluxData(url, renderedScript, uuid)
return { return {
csv: body, csv: body,
didTruncate: byteLength >= MAX_RESPONSE_BYTES, didTruncate: byteLength >= MAX_RESPONSE_BYTES,
ok,
uuid: responseUUID, uuid: responseUUID,
} }
} catch (error) { } catch (error) {
@ -112,7 +115,7 @@ export const getTimeSeries = async (
fluxASTLink: string, fluxASTLink: string,
maxSideLength: number maxSideLength: number
): Promise<GetTimeSeriesResult> => { ): Promise<GetTimeSeriesResult> => {
const {csv, didTruncate, uuid: responseUUID} = await getRawTimeSeries( const {csv, didTruncate, ok, uuid: responseUUID} = await getRawTimeSeries(
source, source,
script, script,
uuid, uuid,
@ -121,6 +124,12 @@ export const getTimeSeries = async (
maxSideLength maxSideLength
) )
if (!ok) {
// error will be string of {error: value}
const error = _.get(JSON.parse(csv), 'error', '')
throw new Error(error)
}
const tables = parseResponse(csv) const tables = parseResponse(csv)
try { try {
@ -136,7 +145,6 @@ export const getTimeSeries = async (
console.error('Could not parse response body', error) console.error('Could not parse response body', error)
return { return {
// REVIEW: Why is this being returned as a `FluxTable[]`?
csv, csv,
tables: parseResponseError(csv), tables: parseResponseError(csv),
didTruncate: false, didTruncate: false,

View File

@ -15,6 +15,7 @@ import RawFluxDataTable from 'src/shared/components/TimeMachine/RawFluxDataTable
import TableGraphTransform from 'src/shared/components/TableGraphTransform' import TableGraphTransform from 'src/shared/components/TableGraphTransform'
import TableGraphFormat from 'src/shared/components/TableGraphFormat' import TableGraphFormat from 'src/shared/components/TableGraphFormat'
import AutoRefresh from 'src/shared/components/AutoRefresh' import AutoRefresh from 'src/shared/components/AutoRefresh'
import InvalidData from 'src/shared/components/InvalidData'
// Constants // Constants
import {emptyGraphCopy} from 'src/shared/copy/cell' import {emptyGraphCopy} from 'src/shared/copy/cell'
@ -166,6 +167,7 @@ class RefreshingGraph extends Component<Props> {
rawFluxData, rawFluxData,
loading, loading,
uuid, uuid,
errorMessage,
}) => { }) => {
const hasValues = const hasValues =
timeSeriesFlux.length || timeSeriesFlux.length ||
@ -180,6 +182,9 @@ class RefreshingGraph extends Component<Props> {
}) })
if (!hasValues) { if (!hasValues) {
if (errorMessage) {
return <InvalidData message={errorMessage} />
}
if (cellNoteVisibility === NoteVisibility.ShowWhenNoData) { if (cellNoteVisibility === NoteVisibility.ShowWhenNoData) {
return <MarkdownCell text={cellNote} /> return <MarkdownCell text={cellNote} />
} }

View File

@ -41,6 +41,7 @@ interface RenderProps {
rawFluxData: string rawFluxData: string
loading: RemoteDataState loading: RemoteDataState
uuid: string uuid: string
errorMessage: string
} }
interface Props { interface Props {
@ -66,6 +67,7 @@ interface State {
timeSeriesInfluxQL: TimeSeriesServerResponse[] timeSeriesInfluxQL: TimeSeriesServerResponse[]
timeSeriesFlux: FluxTable[] timeSeriesFlux: FluxTable[]
latestUUID: string latestUUID: string
errorMessage: string
} }
const TEMP_RES = 300 // FIXME const TEMP_RES = 300 // FIXME
@ -118,6 +120,7 @@ class TimeSeries extends PureComponent<Props, State> {
timeSeriesFlux: [], timeSeriesFlux: [],
rawFluxData: '', rawFluxData: '',
latestUUID: null, latestUUID: null,
errorMessage: '',
} }
} }
@ -147,6 +150,7 @@ class TimeSeries extends PureComponent<Props, State> {
loading, loading,
isFirstFetch, isFirstFetch,
latestUUID, latestUUID,
errorMessage,
} = this.state } = this.state
if (isFirstFetch && loading === RemoteDataState.Loading) { if (isFirstFetch && loading === RemoteDataState.Loading) {
@ -162,6 +166,7 @@ class TimeSeries extends PureComponent<Props, State> {
rawFluxData, rawFluxData,
loading, loading,
uuid: latestUUID, uuid: latestUUID,
errorMessage,
})} })}
</> </>
) )
@ -222,6 +227,8 @@ class TimeSeries extends PureComponent<Props, State> {
isFirstFetch: false, isFirstFetch: false,
}) })
let errorMessage = ''
try { try {
if (this.isFluxQuery) { if (this.isFluxQuery) {
const results = await this.executeFluxQuery(latestUUID) const results = await this.executeFluxQuery(latestUUID)
@ -235,8 +242,9 @@ class TimeSeries extends PureComponent<Props, State> {
} }
loading = RemoteDataState.Done loading = RemoteDataState.Done
} catch { } catch (err) {
loading = RemoteDataState.Error loading = RemoteDataState.Error
errorMessage = err.toString()
} }
this.setState({ this.setState({
@ -245,6 +253,7 @@ class TimeSeries extends PureComponent<Props, State> {
rawFluxData, rawFluxData,
loading, loading,
latestUUID: responseUUID, latestUUID: responseUUID,
errorMessage,
}) })
if (grabDataForDownload) { if (grabDataForDownload) {

View File

@ -64,6 +64,11 @@ export const parseTables = (responseChunk: string): FluxTable[] => {
const nonAnnotationData = Papa.parse(nonAnnotationLines).data const nonAnnotationData = Papa.parse(nonAnnotationLines).data
const annotationData = Papa.parse(annotationLines).data const annotationData = Papa.parse(annotationLines).data
const headerRow: string[] = nonAnnotationData[0] const headerRow: string[] = nonAnnotationData[0]
if (headerRow[1] === 'error' && headerRow[2] === 'reference') {
throw new Error(_.get(nonAnnotationData, '1.1'))
}
const tableColIndex = headerRow.findIndex(h => h === 'table') const tableColIndex = headerRow.findIndex(h => h === 'table')
const timeColIndex = headerRow.findIndex(h => h === '_time') const timeColIndex = headerRow.findIndex(h => h === '_time')

View File

@ -22,6 +22,7 @@ import {LastValues} from 'src/worker/jobs/fluxTablesToSingleStat'
interface DecodeFluxRespWithLimitResult { interface DecodeFluxRespWithLimitResult {
body: string body: string
byteLength: number byteLength: number
ok: boolean
uuid?: string uuid?: string
} }

View File

@ -5,6 +5,7 @@ import {MAX_RESPONSE_BYTES} from 'src/flux/constants'
interface DecodeFluxRespWithLimitResult { interface DecodeFluxRespWithLimitResult {
body: string body: string
byteLength: number byteLength: number
ok: boolean
uuid?: string uuid?: string
} }
@ -42,7 +43,7 @@ export default async (msg: Message): Promise<DecodeFluxRespWithLimitResult> => {
reader.cancel() reader.cancel()
return {body: bodyString, byteLength: bytesRead, uuid} return {body: bodyString, byteLength: bytesRead, ok: response.ok, uuid}
} else { } else {
bodyString += currentText bodyString += currentText
} }
@ -52,5 +53,5 @@ export default async (msg: Message): Promise<DecodeFluxRespWithLimitResult> => {
reader.cancel() reader.cancel()
return {body: bodyString, byteLength: bytesRead, uuid} return {body: bodyString, byteLength: bytesRead, ok: response.ok, uuid}
} }

View File

@ -184,3 +184,11 @@ export const TRUNCATED_RESPONSE = `
#datatype,string,long,dateTime:RFC3339,dateTime:RFC3339,dateTime:RFC3339,long,string,string,string,string,string,string,string #datatype,string,long,dateTime:RFC3339,dateTime:RFC3339,dateTime:RFC3339,long,string,string,string,string,string,string,string
#group,false,false,false,false,false,false,true,true,true,true,true,true,true #group,false,false,false,false,false,false,true,true,true,true,true,true,true
#default,_result,,,,,,,,,,,,` #default,_result,,,,,,,,,,,,`
export const ERROR =
'failed to create physical plan: invalid time bounds from procedure from: bounds contain zero time'
export const ERROR_RESPONSE = `#datatype,string,string
#group,true,true
#default,,
,error,reference
,${ERROR}`

View File

@ -5,6 +5,8 @@ import {
MULTI_SCHEMA_RESPONSE, MULTI_SCHEMA_RESPONSE,
EXPECTED_COLUMNS, EXPECTED_COLUMNS,
TRUNCATED_RESPONSE, TRUNCATED_RESPONSE,
ERROR_RESPONSE,
ERROR,
} from 'test/shared/parsing/flux/constants' } from 'test/shared/parsing/flux/constants'
describe('Flux results parser', () => { describe('Flux results parser', () => {
@ -46,4 +48,10 @@ describe('Flux results parser', () => {
expect(actual).toHaveLength(2) expect(actual).toHaveLength(2)
}) })
}) })
describe('error responses', () => {
it('should throw an error if an error csv ', () => {
expect(() => parseResponse(ERROR_RESPONSE)).toThrowError(ERROR)
})
})
}) })