From a6eca5e935fbc244bfb983c439936ad0a51def6f Mon Sep 17 00:00:00 2001 From: Vadim Ogievetsky Date: Thu, 12 Sep 2019 00:35:04 -0700 Subject: [PATCH] Web console: Force intervals config (#8514) * make sure intervals are required * all truncated values everywhere * continue to spec when going from tasks table * remove unused thigns * fix alert --- .../components/array-input/array-input.tsx | 6 +- .../src/components/auto-form/auto-form.tsx | 8 ++- .../src/components/table-cell/table-cell.tsx | 60 ++++++++++++------- web-console/src/utils/ingestion-spec.tsx | 6 +- .../views/load-data-view/load-data-view.tsx | 39 ++++++------ .../parse-data-table.spec.tsx | 1 - .../parse-data-table/parse-data-table.tsx | 3 +- 7 files changed, 75 insertions(+), 48 deletions(-) diff --git a/web-console/src/components/array-input/array-input.tsx b/web-console/src/components/array-input/array-input.tsx index 5411f6f893c..de4fbd07fb5 100644 --- a/web-console/src/components/array-input/array-input.tsx +++ b/web-console/src/components/array-input/array-input.tsx @@ -16,7 +16,7 @@ * limitations under the License. */ -import { TextArea } from '@blueprintjs/core'; +import { Intent, TextArea } from '@blueprintjs/core'; import React from 'react'; import { compact } from '../../utils'; @@ -28,6 +28,7 @@ export interface ArrayInputProps { placeholder?: string; large?: boolean; disabled?: boolean; + intent?: Intent; } export class ArrayInput extends React.PureComponent { @@ -51,7 +52,7 @@ export class ArrayInput extends React.PureComponent ); diff --git a/web-console/src/components/auto-form/auto-form.tsx b/web-console/src/components/auto-form/auto-form.tsx index 15c3f51c13a..4ff5856ede0 100644 --- a/web-console/src/components/auto-form/auto-form.tsx +++ b/web-console/src/components/auto-form/auto-form.tsx @@ -244,15 +244,21 @@ export class AutoForm> extends React.PureComponent private renderStringArrayInput(field: Field): JSX.Element { const { model, large } = this.props; + const modelValue = deepGet(model as any, field.name); return ( { this.fieldChange(field, v); }} placeholder={field.placeholder} large={large} disabled={AutoForm.evaluateFunctor(field.disabled, model)} + intent={ + AutoForm.evaluateFunctor(field.required, model) && modelValue == null + ? Intent.PRIMARY + : undefined + } /> ); } diff --git a/web-console/src/components/table-cell/table-cell.tsx b/web-console/src/components/table-cell/table-cell.tsx index 5a6b535a47b..8d019fe32a0 100644 --- a/web-console/src/components/table-cell/table-cell.tsx +++ b/web-console/src/components/table-cell/table-cell.tsx @@ -19,15 +19,19 @@ import { IconNames } from '@blueprintjs/icons'; import React from 'react'; +import { ShowValueDialog } from '../../dialogs/show-value-dialog/show-value-dialog'; import { ActionIcon } from '../action-icon/action-icon'; import './table-cell.scss'; -export interface NullTableCellProps { +export interface TableCellProps { value?: any; timestamp?: boolean; unparseable?: boolean; - openModal?: (str: string) => void; +} + +export interface TableCellState { + showValue?: string; } interface ShortParts { @@ -36,26 +40,9 @@ interface ShortParts { suffix: string; } -export class TableCell extends React.PureComponent { +export class TableCell extends React.PureComponent { static MAX_CHARS_TO_SHOW = 50; - possiblyTruncate(str: string): React.ReactNode { - if (str.length <= TableCell.MAX_CHARS_TO_SHOW) return str; - - const { prefix, omitted, suffix } = TableCell.shortenString(str); - return ( - - {prefix} - {omitted} - {suffix} - (this.props.openModal ? this.props.openModal(str) : null)} - /> - - ); - } - static shortenString(str: string): ShortParts { // Print something like: // BAAAArAAEiQKpDAEAACwZCBAGSBgiSEAAAAQpAIDwAg...23 omitted...gwiRoQBJIC @@ -69,6 +56,35 @@ export class TableCell extends React.PureComponent { }; } + constructor(props: TableCellProps) { + super(props); + this.state = {}; + } + + private renderShowValueDialog(): JSX.Element | undefined { + const { showValue } = this.state; + if (!showValue) return; + + return ( + this.setState({ showValue: undefined })} str={showValue} /> + ); + } + + private renderTruncated(str: string): React.ReactNode { + if (str.length <= TableCell.MAX_CHARS_TO_SHOW) return str; + + const { prefix, omitted, suffix } = TableCell.shortenString(str); + return ( + + {prefix} + {omitted} + {suffix} + this.setState({ showValue: str })} /> + {this.renderShowValueDialog()} + + ); + } + render(): React.ReactNode { const { value, timestamp, unparseable } = this.props; if (unparseable) { @@ -81,9 +97,9 @@ export class TableCell extends React.PureComponent { ); } else if (Array.isArray(value)) { - return this.possiblyTruncate(`[${value.join(', ')}]`); + return this.renderTruncated(`[${value.join(', ')}]`); } else { - return this.possiblyTruncate(String(value)); + return this.renderTruncated(String(value)); } } else { if (timestamp) { diff --git a/web-console/src/utils/ingestion-spec.tsx b/web-console/src/utils/ingestion-spec.tsx index aa04bf3daf9..952d3baecb1 100644 --- a/web-console/src/utils/ingestion-spec.tsx +++ b/web-console/src/utils/ingestion-spec.tsx @@ -588,7 +588,7 @@ export interface GranularitySpec { queryGranularity?: string; segmentGranularity?: string; rollup?: boolean; - intervals?: string; + intervals?: string | string[]; } export interface MetricSpec { @@ -1541,11 +1541,11 @@ export interface TuningConfig { fetchThreads?: number; } -export function invalidTuningConfig(tuningConfig: TuningConfig): boolean { +export function invalidTuningConfig(tuningConfig: TuningConfig, intervals: any): boolean { return Boolean( tuningConfig.type === 'index_parallel' && tuningConfig.forceGuaranteedRollup && - !tuningConfig.numShards, + (!tuningConfig.numShards || !intervals), ); } diff --git a/web-console/src/views/load-data-view/load-data-view.tsx b/web-console/src/views/load-data-view/load-data-view.tsx index 00eb64b33cd..87e1853ba1e 100644 --- a/web-console/src/views/load-data-view/load-data-view.tsx +++ b/web-console/src/views/load-data-view/load-data-view.tsx @@ -50,7 +50,6 @@ import { Loader, } from '../../components'; import { AsyncActionDialog } from '../../dialogs'; -import { ShowValueDialog } from '../../dialogs/show-value-dialog/show-value-dialog'; import { AppToaster } from '../../singletons/toaster'; import { UrlBaser } from '../../singletons/url-baser'; import { @@ -251,8 +250,6 @@ export interface LoadDataViewState { showResetConfirm: boolean; newRollup?: boolean; newDimensionMode?: DimensionMode; - showViewValueModal: boolean; - str: string; // welcome overlordModules?: string[]; @@ -317,8 +314,6 @@ export class LoadDataView extends React.PureComponent ); } @@ -651,15 +645,6 @@ export class LoadDataView extends React.PureComponent this.setState({ showViewValueModal: false })} str={str} /> - ); - } - renderWelcomeStepMessage(): JSX.Element | undefined { const { selectedComboType, exampleManifests } = this.state; @@ -1225,7 +1210,6 @@ export class LoadDataView extends React.PureComponent this.setState({ showViewValueModal: true, str: str })} sampleData={parserQueryState.data} columnFilter={columnFilter} canFlatten={canFlatten} @@ -2649,6 +2633,25 @@ export class LoadDataView extends React.PureComponent this.updateSpec(deepSet(spec, 'tuningConfig', t))} /> + Boolean(deepGet(s, 'tuningConfig.forceGuaranteedRollup')), + info: ( + <> + A comma separated list of intervals for the raw data being ingested. Ignored for + real-time ingestion. + + ), + }, + ]} + model={spec} + onChange={s => this.updateSpec(s)} + />
@@ -2658,7 +2661,7 @@ export class LoadDataView extends React.PureComponent {this.renderNextBar({ - disabled: invalidTuningConfig(tuningConfig), + disabled: invalidTuningConfig(tuningConfig, granularitySpec.intervals), })} ); @@ -2864,6 +2867,7 @@ export class LoadDataView extends React.PureComponent { const parseDataTable = ( {}} sampleData={sampleData} columnFilter="" canFlatten={false} diff --git a/web-console/src/views/load-data-view/parse-data-table/parse-data-table.tsx b/web-console/src/views/load-data-view/parse-data-table/parse-data-table.tsx index 2d00968d7b1..380eab29e17 100644 --- a/web-console/src/views/load-data-view/parse-data-table/parse-data-table.tsx +++ b/web-console/src/views/load-data-view/parse-data-table/parse-data-table.tsx @@ -34,7 +34,6 @@ export interface ParseDataTableProps { flattenedColumnsOnly: boolean; flattenFields: FlattenField[]; onFlattenFieldSelect: (field: FlattenField, index: number) => void; - openModal: (str: string) => void; } export class ParseDataTable extends React.PureComponent { @@ -78,7 +77,7 @@ export class ParseDataTable extends React.PureComponent { if (row.original.unparseable) { return ; } - return this.props.openModal(str)} />; + return ; }, headerClassName: classNames({ flattened: flattenField,