mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 09:48:58 -04:00
[Data views] Implement persistable state (#132959)
* Tmp commit * Use serializable version * Update tests * Add test for fields * Use spec instead of base * Update types * Fix type errors * Fix tests & types * Update types * Fix lint Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com>
This commit is contained in:
parent
1b2c58f58e
commit
6a7ad6fc4f
26 changed files with 165 additions and 99 deletions
|
@ -14,17 +14,19 @@ import * as estypes from '@elastic/elasticsearch/lib/api/typesWithBodyKey';
|
|||
*/
|
||||
export type IFieldSubType = IFieldSubTypeMultiOptional | IFieldSubTypeNestedOptional;
|
||||
|
||||
export interface IFieldSubTypeMultiOptional {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type IFieldSubTypeMultiOptional = {
|
||||
multi?: { parent: string };
|
||||
}
|
||||
};
|
||||
|
||||
export interface IFieldSubTypeMulti {
|
||||
multi: { parent: string };
|
||||
}
|
||||
|
||||
export interface IFieldSubTypeNestedOptional {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type IFieldSubTypeNestedOptional = {
|
||||
nested?: { path: string };
|
||||
}
|
||||
};
|
||||
|
||||
export interface IFieldSubTypeNested {
|
||||
nested: { path: string };
|
||||
|
@ -34,7 +36,8 @@ export interface IFieldSubTypeNested {
|
|||
* A base interface for an index pattern field
|
||||
* @public
|
||||
*/
|
||||
export interface DataViewFieldBase {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type DataViewFieldBase = {
|
||||
name: string;
|
||||
/**
|
||||
* Kibana field type
|
||||
|
@ -46,22 +49,23 @@ export interface DataViewFieldBase {
|
|||
*/
|
||||
script?: string;
|
||||
/**
|
||||
* Scripted field langauge
|
||||
* Scripted field language
|
||||
* Painless is the only valid scripted field language
|
||||
*/
|
||||
lang?: estypes.ScriptLanguage;
|
||||
scripted?: boolean;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* A base interface for an index pattern
|
||||
* @public
|
||||
*/
|
||||
export interface DataViewBase {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type DataViewBase = {
|
||||
fields: DataViewFieldBase[];
|
||||
id?: string;
|
||||
title: string;
|
||||
}
|
||||
};
|
||||
|
||||
export interface BoolQuery {
|
||||
must: estypes.QueryDslQueryContainer[];
|
||||
|
|
|
@ -24,7 +24,7 @@ export interface Dimension {
|
|||
accessor: number;
|
||||
format: {
|
||||
id?: string;
|
||||
params?: SerializedFieldFormat<object>;
|
||||
params?: SerializedFieldFormat;
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -129,7 +129,7 @@ export enum LegendDisplay {
|
|||
export interface BucketColumns extends DatatableColumn {
|
||||
format?: {
|
||||
id?: string;
|
||||
params?: SerializedFieldFormat<object>;
|
||||
params?: SerializedFieldFormat;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -18,12 +18,7 @@ import {
|
|||
XYChartSeriesIdentifier,
|
||||
} from '@elastic/charts';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import {
|
||||
FieldFormat,
|
||||
FieldFormatParams,
|
||||
IFieldFormat,
|
||||
SerializedFieldFormat,
|
||||
} from '@kbn/field-formats-plugin/common';
|
||||
import { FieldFormat, IFieldFormat, SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
import { Datatable } from '@kbn/expressions-plugin';
|
||||
import {
|
||||
getFormatByAccessor,
|
||||
|
@ -64,7 +59,7 @@ type GetSeriesNameFn = (
|
|||
config: {
|
||||
splitColumnId?: string;
|
||||
accessorsCount: number;
|
||||
splitHint: SerializedFieldFormat<FieldFormatParams> | undefined;
|
||||
splitHint: SerializedFieldFormat | undefined;
|
||||
splitFormatter: FieldFormat;
|
||||
alreadyFormattedColumns: Record<string, boolean>;
|
||||
columnToLabelMap: Record<string, string>;
|
||||
|
|
|
@ -14,6 +14,7 @@ import { Assign, Ensure } from '@kbn/utility-types';
|
|||
|
||||
import { ExpressionAstExpression, ExpressionAstArgument } from '@kbn/expressions-plugin/common';
|
||||
import type { SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
import { FieldFormatParams } from '@kbn/field-formats-plugin/common';
|
||||
// eslint-disable-next-line @kbn/eslint/no-restricted-paths
|
||||
import { ISearchOptions, ISearchSource } from '../../../public';
|
||||
|
||||
|
@ -325,9 +326,7 @@ export class AggConfig {
|
|||
*
|
||||
* @public
|
||||
*/
|
||||
toSerializedFieldFormat():
|
||||
| {}
|
||||
| Ensure<SerializedFieldFormat<SerializableRecord>, SerializableRecord> {
|
||||
toSerializedFieldFormat<T extends FieldFormatParams>(): SerializedFieldFormat<T> {
|
||||
return this.type ? this.type.getSerializedFormat(this) : {};
|
||||
}
|
||||
|
||||
|
|
|
@ -14,6 +14,7 @@ import type { RequestAdapter } from '@kbn/inspector-plugin/common';
|
|||
import type { SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
|
||||
import type * as estypes from '@elastic/elasticsearch/lib/api/typesWithBodyKey';
|
||||
import { FieldFormatParams } from '@kbn/field-formats-plugin/common';
|
||||
// eslint-disable-next-line @kbn/eslint/no-restricted-paths
|
||||
import { ISearchSource } from '../../../public';
|
||||
import { initParams } from './agg_params';
|
||||
|
@ -208,7 +209,7 @@ export class AggType<
|
|||
* @param {agg} agg - the agg to pick a format for
|
||||
* @return {SerializedFieldFormat}
|
||||
*/
|
||||
getSerializedFormat: (agg: TAggConfig) => SerializedFieldFormat;
|
||||
getSerializedFormat: <T extends FieldFormatParams>(agg: TAggConfig) => SerializedFieldFormat<T>;
|
||||
|
||||
getValue: (agg: TAggConfig, bucket: any) => any;
|
||||
|
||||
|
|
|
@ -12,7 +12,6 @@ import { i18n } from '@kbn/i18n';
|
|||
import {
|
||||
FieldFormat,
|
||||
FieldFormatInstanceType,
|
||||
FieldFormatParams,
|
||||
FieldFormatsContentType,
|
||||
IFieldFormat,
|
||||
SerializedFieldFormat,
|
||||
|
@ -129,13 +128,13 @@ export function getAggsFormats(getFieldFormat: GetFieldFormat): FieldFormatInsta
|
|||
|
||||
convert = (val: string, type: FieldFormatsContentType) => {
|
||||
const params = this._params;
|
||||
const format = getFieldFormat({ id: params.id, params });
|
||||
const format = getFieldFormat({ id: `${params.id}`, params });
|
||||
|
||||
if (val === '__other__') {
|
||||
return params.otherBucketLabel;
|
||||
return `${params.otherBucketLabel}`;
|
||||
}
|
||||
if (val === '__missing__') {
|
||||
return params.missingBucketLabel;
|
||||
return `${params.missingBucketLabel}`;
|
||||
}
|
||||
|
||||
return format.convert(val, type);
|
||||
|
@ -146,7 +145,7 @@ export function getAggsFormats(getFieldFormat: GetFieldFormat): FieldFormatInsta
|
|||
static id = 'multi_terms';
|
||||
static hidden = true;
|
||||
|
||||
private formatCache: Map<SerializedFieldFormat<FieldFormatParams>, FieldFormat> = new Map();
|
||||
private formatCache: Map<SerializedFieldFormat, FieldFormat> = new Map();
|
||||
|
||||
convert = (val: unknown, type: FieldFormatsContentType) => {
|
||||
const params = this._params;
|
||||
|
@ -160,10 +159,10 @@ export function getAggsFormats(getFieldFormat: GetFieldFormat): FieldFormatInsta
|
|||
});
|
||||
|
||||
if (String(val) === '__other__') {
|
||||
return params.otherBucketLabel;
|
||||
return `${params.otherBucketLabel}`;
|
||||
}
|
||||
|
||||
const joinTemplate = params.separator ?? ' › ';
|
||||
const joinTemplate = `${params.separator ?? ' › '}`;
|
||||
|
||||
return (val as MultiFieldKey).keys
|
||||
.map((valPart, i) => formats[i].convert(valPart, type))
|
||||
|
|
|
@ -35,7 +35,7 @@ export class DateFormatEditor extends DefaultFormatEditor<DateFormatEditorFormat
|
|||
render() {
|
||||
const { format, formatParams } = this.props;
|
||||
const { error, samples } = this.state;
|
||||
const defaultPattern = format.getParamDefaults().pattern;
|
||||
const defaultPattern = `${format.getParamDefaults().pattern}`;
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
|
|
|
@ -34,7 +34,7 @@ export class DateNanosFormatEditor extends DefaultFormatEditor<DateNanosFormatEd
|
|||
render() {
|
||||
const { format, formatParams } = this.props;
|
||||
const { error, samples } = this.state;
|
||||
const defaultPattern = format.getParamDefaults().pattern;
|
||||
const defaultPattern = `${format.getParamDefaults().pattern}`;
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
|
|
|
@ -86,7 +86,7 @@ export class DurationFormatEditor extends DefaultFormatEditor<
|
|||
const { error, samples, hasDecimalError } = this.state;
|
||||
|
||||
const formatParams: DurationFormatEditorFormatParams = {
|
||||
includeSpaceWithSuffix: format.getParamDefaults().includeSpaceWithSuffix,
|
||||
includeSpaceWithSuffix: format.getParamDefaults().includeSpaceWithSuffix as boolean,
|
||||
...this.props.formatParams,
|
||||
};
|
||||
|
||||
|
|
|
@ -34,7 +34,7 @@ export class NumberFormatEditor extends DefaultFormatEditor<NumberFormatEditorPa
|
|||
render() {
|
||||
const { format, formatParams } = this.props;
|
||||
const { error, samples } = this.state;
|
||||
const defaultPattern = format.getParamDefaults().pattern;
|
||||
const defaultPattern = `${format.getParamDefaults().pattern}`;
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
|
|
|
@ -148,7 +148,7 @@ export class UrlFormatEditor extends DefaultFormatEditor<
|
|||
const { formatParams, format } = this.props;
|
||||
const { error, samples, sampleConverterType } = this.state;
|
||||
|
||||
const urlType = formatParams.type ?? format.getParamDefaults().type;
|
||||
const urlType = formatParams.type ?? `${format.getParamDefaults().type}`;
|
||||
return (
|
||||
<Fragment>
|
||||
<EuiFormRow
|
||||
|
|
|
@ -33,7 +33,7 @@ import {
|
|||
import { i18n } from '@kbn/i18n';
|
||||
import { FormattedMessage } from '@kbn/i18n-react';
|
||||
import { PainlessLang } from '@kbn/monaco';
|
||||
import type { FieldFormatInstanceType } from '@kbn/field-formats-plugin/common';
|
||||
import type { FieldFormatInstanceType, FieldFormatParams } from '@kbn/field-formats-plugin/common';
|
||||
import type { FieldFormatsStart } from '@kbn/field-formats-plugin/public';
|
||||
import { KBN_FIELD_TYPES, ES_FIELD_TYPES } from '@kbn/field-types';
|
||||
import { DataView, DataViewField, DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public';
|
||||
|
@ -97,7 +97,7 @@ export interface FieldEditorState {
|
|||
fieldTypeFormats: FieldTypeFormat[];
|
||||
existingFieldNames: string[];
|
||||
fieldFormatId?: string;
|
||||
fieldFormatParams: { [key: string]: unknown };
|
||||
fieldFormatParams: FieldFormatParams;
|
||||
showScriptingHelp: boolean;
|
||||
showDeleteModal: boolean;
|
||||
hasFormatError: boolean;
|
||||
|
|
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0 and the Server Side Public License, v 1; you may not use this file except
|
||||
* in compliance with, at your election, the Elastic License 2.0 or the Server
|
||||
* Side Public License, v 1.
|
||||
*/
|
||||
|
||||
import { DataViewPersistableStateService } from './persistable_state';
|
||||
import { SavedObjectReference } from '@kbn/core/types';
|
||||
import { DataViewSpec } from '../types';
|
||||
const { inject, extract } = DataViewPersistableStateService;
|
||||
|
||||
describe('data view persistable state tests', () => {
|
||||
test('inject references', () => {
|
||||
const state: DataViewSpec = {
|
||||
id: 'my-id',
|
||||
title: 'my-title',
|
||||
fields: {},
|
||||
};
|
||||
const references: SavedObjectReference[] = [];
|
||||
|
||||
const result = inject(state, references);
|
||||
|
||||
expect(result).toBe(state);
|
||||
});
|
||||
|
||||
test('extract references', () => {
|
||||
const state: DataViewSpec = {
|
||||
id: 'my-id',
|
||||
title: 'my-title',
|
||||
fields: {},
|
||||
};
|
||||
|
||||
const result = extract(state);
|
||||
|
||||
expect(result.state).toBe(state);
|
||||
expect(result.references).toEqual([]);
|
||||
});
|
||||
});
|
|
@ -0,0 +1,22 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0 and the Server Side Public License, v 1; you may not use this file except
|
||||
* in compliance with, at your election, the Elastic License 2.0 or the Server
|
||||
* Side Public License, v 1.
|
||||
*/
|
||||
|
||||
import { PersistableStateService } from '@kbn/kibana-utils-plugin/common';
|
||||
import { DataViewSpec } from '../types';
|
||||
|
||||
export const DataViewPersistableStateService: PersistableStateService<DataViewSpec> = {
|
||||
inject: (state, references) => {
|
||||
return state;
|
||||
},
|
||||
extract: (state) => {
|
||||
return { state, references: [] };
|
||||
},
|
||||
getAllMigrations: () => ({}),
|
||||
migrateToLatest: ({ state }) => state,
|
||||
telemetry: () => ({}),
|
||||
};
|
|
@ -36,7 +36,8 @@ export type RuntimeTypeExceptComposite = Exclude<RuntimeType, 'composite'>;
|
|||
* Runtime field definition
|
||||
* @public
|
||||
*/
|
||||
export interface RuntimeFieldBase {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type RuntimeFieldBase = {
|
||||
/**
|
||||
* Type of runtime field
|
||||
*/
|
||||
|
@ -50,12 +51,12 @@ export interface RuntimeFieldBase {
|
|||
*/
|
||||
source: string;
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* The RuntimeField that will be sent in the ES Query "runtime_mappings" object
|
||||
*/
|
||||
export interface RuntimeFieldSpec extends RuntimeFieldBase {
|
||||
export type RuntimeFieldSpec = RuntimeFieldBase & {
|
||||
fields?: Record<
|
||||
string,
|
||||
{
|
||||
|
@ -63,7 +64,7 @@ export interface RuntimeFieldSpec extends RuntimeFieldBase {
|
|||
type: RuntimeTypeExceptComposite;
|
||||
}
|
||||
>;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Field attributes that are user configurable
|
||||
|
@ -159,15 +160,17 @@ export interface DataViewAttributes {
|
|||
* @public
|
||||
* Storage of field attributes. Necessary since the field list isn't saved.
|
||||
*/
|
||||
export interface FieldAttrs {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type FieldAttrs = {
|
||||
[key: string]: FieldAttrSet;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Field attributes that are stored on the data view
|
||||
* @public
|
||||
*/
|
||||
export interface FieldAttrSet {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type FieldAttrSet = {
|
||||
/**
|
||||
* Custom field label
|
||||
*/
|
||||
|
@ -176,7 +179,7 @@ export interface FieldAttrSet {
|
|||
* Popularity count - used for discover
|
||||
*/
|
||||
count?: number;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Handler for data view notifications
|
||||
|
@ -328,7 +331,8 @@ export type AggregationRestrictions = Record<
|
|||
/**
|
||||
* Interface for metadata about rollup indices
|
||||
*/
|
||||
export interface TypeMeta {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type TypeMeta = {
|
||||
/**
|
||||
* Aggregation restrictions for rollup fields
|
||||
*/
|
||||
|
@ -342,7 +346,7 @@ export interface TypeMeta {
|
|||
*/
|
||||
rollup_index: string;
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Data View type. Default or rollup
|
||||
|
@ -358,7 +362,7 @@ export type FieldSpecConflictDescriptions = Record<string, string[]>;
|
|||
* Serialized version of DataViewField
|
||||
* @public
|
||||
*/
|
||||
export interface FieldSpec extends DataViewFieldBase {
|
||||
export type FieldSpec = DataViewFieldBase & {
|
||||
/**
|
||||
* Popularity count is used by discover
|
||||
*/
|
||||
|
@ -410,7 +414,7 @@ export interface FieldSpec extends DataViewFieldBase {
|
|||
* Is this field in the mapping? False if a scripted or runtime field defined on the data view.
|
||||
*/
|
||||
isMapped?: boolean;
|
||||
}
|
||||
};
|
||||
|
||||
export type DataViewFieldMap = Record<string, FieldSpec>;
|
||||
|
||||
|
@ -418,7 +422,8 @@ export type DataViewFieldMap = Record<string, FieldSpec>;
|
|||
* Static data view format
|
||||
* Serialized data object, representing data view attributes and state
|
||||
*/
|
||||
export interface DataViewSpec {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type DataViewSpec = {
|
||||
/**
|
||||
* Saved object id
|
||||
*/
|
||||
|
@ -471,11 +476,12 @@ export interface DataViewSpec {
|
|||
* Array of namespace ids
|
||||
*/
|
||||
namespaces?: string[];
|
||||
}
|
||||
};
|
||||
|
||||
export interface SourceFilter {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type SourceFilter = {
|
||||
value: string;
|
||||
}
|
||||
};
|
||||
|
||||
export interface HasDataService {
|
||||
hasESData: () => Promise<boolean>;
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
import { UsageCounter } from '@kbn/usage-collection-plugin/server';
|
||||
import { schema } from '@kbn/config-schema';
|
||||
import { IRouter, StartServicesAccessor } from '@kbn/core/server';
|
||||
import { FieldFormatParams, SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
import { SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
import { DataViewsService } from '../../../common';
|
||||
import { handleErrors } from '../util/handle_errors';
|
||||
import { serializedFieldFormatSchema } from '../util/schemas';
|
||||
|
@ -83,7 +83,7 @@ export const updateFields = async ({
|
|||
interface FieldUpdateType {
|
||||
customLabel?: string | null;
|
||||
count?: number | null;
|
||||
format?: SerializedFieldFormat<FieldFormatParams> | null;
|
||||
format?: SerializedFieldFormat | null;
|
||||
}
|
||||
|
||||
const fieldUpdateSchema = schema.object({
|
||||
|
|
|
@ -192,7 +192,7 @@ export abstract class FieldFormat {
|
|||
|
||||
const params = transform(
|
||||
this._params,
|
||||
(uniqParams: FieldFormatParams & FieldFormatMetaParams, val: unknown, param: string) => {
|
||||
(uniqParams: FieldFormatParams & FieldFormatMetaParams, val, param: string) => {
|
||||
if (param === 'parsedUrl') return;
|
||||
if (param && val !== get(defaultsParams, param)) {
|
||||
uniqParams[param] = val;
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
* Side Public License, v 1.
|
||||
*/
|
||||
|
||||
import { Serializable, SerializableRecord } from '@kbn/utility-types';
|
||||
import { FieldFormat } from './field_format';
|
||||
import { FieldFormatsRegistry } from './field_formats_registry';
|
||||
|
||||
|
@ -77,11 +78,12 @@ export enum FIELD_FORMAT_IDS {
|
|||
}
|
||||
|
||||
/** @public */
|
||||
export interface FieldFormatConfig {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type FieldFormatConfig = {
|
||||
id: FieldFormatId;
|
||||
params: FieldFormatParams;
|
||||
es?: boolean;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* If a service is being shared on both the client and the server, and
|
||||
|
@ -95,7 +97,10 @@ export interface FieldFormatConfig {
|
|||
*
|
||||
@public
|
||||
*/
|
||||
export type FieldFormatsGetConfigFn<T = unknown> = (key: string, defaultOverride?: T) => T;
|
||||
export type FieldFormatsGetConfigFn<T extends Serializable = Serializable> = (
|
||||
key: string,
|
||||
defaultOverride?: T
|
||||
) => T;
|
||||
|
||||
export type IFieldFormat = FieldFormat;
|
||||
|
||||
|
@ -126,9 +131,7 @@ export type FieldFormatInstanceType = (new (
|
|||
* TODO: support strict typing for params depending on format type
|
||||
* https://github.com/elastic/kibana/issues/108158
|
||||
*/
|
||||
export interface FieldFormatParams {
|
||||
[param: string]: any;
|
||||
}
|
||||
export type FieldFormatParams = SerializableRecord;
|
||||
|
||||
/**
|
||||
* Params provided by the registry to every field formatter
|
||||
|
@ -152,9 +155,10 @@ export type FieldFormatsStartCommon = Omit<FieldFormatsRegistry, 'init' | 'regis
|
|||
*
|
||||
* @public
|
||||
*/
|
||||
export interface SerializedFieldFormat<TParams = FieldFormatParams> {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-definitions
|
||||
export type SerializedFieldFormat<TParams extends FieldFormatParams = FieldFormatParams> = {
|
||||
id?: string;
|
||||
params?: TParams;
|
||||
}
|
||||
};
|
||||
|
||||
export type FormatFactory = (mapping?: SerializedFieldFormat) => IFieldFormat;
|
||||
|
|
|
@ -159,7 +159,7 @@ export interface PersistableStateService<P extends Serializable = Serializable>
|
|||
* @param version Current semver version of the `state`.
|
||||
* @returns A serializable state object migrated to the latest state.
|
||||
*/
|
||||
migrateToLatest?: (state: VersionedState) => P;
|
||||
migrateToLatest?: (state: VersionedState<P>) => P;
|
||||
|
||||
/**
|
||||
* returns all registered migrations
|
||||
|
|
|
@ -14,7 +14,7 @@ export interface Dimension {
|
|||
accessor: number;
|
||||
format: {
|
||||
id?: string;
|
||||
params?: SerializedFieldFormat<object>;
|
||||
params?: SerializedFieldFormat;
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { Datatable, DatatableColumn } from '@kbn/expressions-plugin/common';
|
||||
import { FieldFormatParams, SerializedFieldFormat } from '@kbn/field-formats-plugin/common/types';
|
||||
import { SerializedFieldFormat } from '@kbn/field-formats-plugin/common/types';
|
||||
import { ExpressionValueVisDimension } from '../expression_functions';
|
||||
|
||||
const getAccessorByIndex = (accessor: number, columns: Datatable['columns']) =>
|
||||
|
@ -68,7 +68,7 @@ export function getAccessor(dimension: string | ExpressionValueVisDimension) {
|
|||
export function getFormatByAccessor(
|
||||
dimension: string | ExpressionValueVisDimension,
|
||||
columns: DatatableColumn[],
|
||||
defaultColumnFormat?: SerializedFieldFormat<FieldFormatParams>
|
||||
defaultColumnFormat?: SerializedFieldFormat
|
||||
) {
|
||||
return typeof dimension === 'string'
|
||||
? getColumnByAccessor(dimension, columns)?.meta.params || defaultColumnFormat
|
||||
|
|
|
@ -67,7 +67,7 @@ export const formatColumnFn: FormatColumnExpressionFunction['fn'] = (
|
|||
};
|
||||
// Some parent formatters are multi-fields and wrap the custom format into a "paramsPerField"
|
||||
// property. Here the format is passed to this property to make it work properly
|
||||
if (col.meta.params?.params?.paramsPerField?.length) {
|
||||
if ((col.meta.params?.params?.paramsPerField as SerializedFieldFormat[])?.length) {
|
||||
return withParams(col, {
|
||||
id: parentFormatId,
|
||||
params: {
|
||||
|
@ -77,13 +77,13 @@ export const formatColumnFn: FormatColumnExpressionFunction['fn'] = (
|
|||
// some wrapper formatters require params to be flatten out (i.e. terms) while others
|
||||
// require them to be in the params property (i.e. ranges)
|
||||
// so for now duplicate
|
||||
paramsPerField: col.meta.params?.params?.paramsPerField.map(
|
||||
(f: { id: string | undefined; params: Record<string, unknown> | undefined }) => ({
|
||||
...f,
|
||||
params: { ...f.params, ...customParams },
|
||||
...customParams,
|
||||
})
|
||||
),
|
||||
paramsPerField: (
|
||||
col.meta.params?.params?.paramsPerField as SerializedFieldFormat[]
|
||||
).map((f) => ({
|
||||
...f,
|
||||
params: { ...f.params, ...customParams },
|
||||
...customParams,
|
||||
})),
|
||||
},
|
||||
});
|
||||
}
|
||||
|
|
|
@ -11,11 +11,7 @@ import { act } from 'react-dom/test-utils';
|
|||
import { mountWithIntl } from '@kbn/test-jest-helpers';
|
||||
import { EuiDataGrid } from '@elastic/eui';
|
||||
import { IAggType } from '@kbn/data-plugin/public';
|
||||
import {
|
||||
FieldFormatParams,
|
||||
IFieldFormat,
|
||||
SerializedFieldFormat,
|
||||
} from '@kbn/field-formats-plugin/common';
|
||||
import { IFieldFormat, SerializedFieldFormat } from '@kbn/field-formats-plugin/common';
|
||||
import { VisualizationContainer } from '../../visualization_container';
|
||||
import { EmptyPlaceholder } from '@kbn/charts-plugin/public';
|
||||
import { LensIconChartDatatable } from '../../assets/chart_datatable';
|
||||
|
@ -110,7 +106,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
paletteService={chartPluginMock.createPaletteRegistry()}
|
||||
|
@ -130,7 +126,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
rowHasRowClickTriggerActions={[true, true, true]}
|
||||
|
@ -151,7 +147,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
rowHasRowClickTriggerActions={[false, false, false]}
|
||||
|
@ -729,7 +725,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
paletteService={chartPluginMock.createPaletteRegistry()}
|
||||
|
@ -764,7 +760,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
paletteService={chartPluginMock.createPaletteRegistry()}
|
||||
|
@ -789,7 +785,7 @@ describe('DatatableComponent', () => {
|
|||
|
||||
const defaultProps = {
|
||||
data,
|
||||
formatFactory: (x?: SerializedFieldFormat<FieldFormatParams>) => x as IFieldFormat,
|
||||
formatFactory: (x?: SerializedFieldFormat) => x as unknown as IFieldFormat,
|
||||
dispatchEvent: onDispatchEvent,
|
||||
getType: jest.fn(),
|
||||
paletteService: chartPluginMock.createPaletteRegistry(),
|
||||
|
@ -825,7 +821,7 @@ describe('DatatableComponent', () => {
|
|||
<DatatableComponent
|
||||
data={data}
|
||||
args={args}
|
||||
formatFactory={(x) => x as IFieldFormat}
|
||||
formatFactory={(x) => x as unknown as IFieldFormat}
|
||||
dispatchEvent={onDispatchEvent}
|
||||
getType={jest.fn()}
|
||||
paletteService={chartPluginMock.createPaletteRegistry()}
|
||||
|
|
|
@ -5,18 +5,18 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import { FIELD_FORMAT_IDS } from '@kbn/field-formats-plugin/common';
|
||||
import { FIELD_FORMAT_IDS, FieldFormatParams } from '@kbn/field-formats-plugin/common';
|
||||
import { useMlKibana } from './kibana_context';
|
||||
|
||||
/**
|
||||
* Set of reasonable defaults for formatters for the ML app.
|
||||
*/
|
||||
const defaultParam = {
|
||||
const defaultParam: Record<string, FieldFormatParams> = {
|
||||
[FIELD_FORMAT_IDS.DURATION]: {
|
||||
inputFormat: 'milliseconds',
|
||||
outputFormat: 'humanizePrecise',
|
||||
},
|
||||
} as Record<FIELD_FORMAT_IDS, object | undefined>;
|
||||
};
|
||||
|
||||
export function useFieldFormatter(fieldType: FIELD_FORMAT_IDS) {
|
||||
const {
|
||||
|
|
|
@ -18,6 +18,10 @@ import type {
|
|||
|
||||
import type { PersistableFilter } from '@kbn/lens-plugin/common';
|
||||
import type { DataView } from '@kbn/data-views-plugin/common';
|
||||
import {
|
||||
FieldFormatParams as BaseFieldFormatParams,
|
||||
SerializedFieldFormat,
|
||||
} from '@kbn/field-formats-plugin/common';
|
||||
|
||||
export const ReportViewTypes = {
|
||||
dist: 'data-distribution',
|
||||
|
@ -121,11 +125,10 @@ export interface ConfigProps {
|
|||
|
||||
export type AppDataType = 'synthetics' | 'ux' | 'infra_logs' | 'infra_metrics' | 'apm' | 'mobile';
|
||||
|
||||
type FormatType = 'duration' | 'number' | 'bytes' | 'percent';
|
||||
type InputFormat = 'microseconds' | 'milliseconds' | 'seconds';
|
||||
type OutputFormat = 'asSeconds' | 'asMilliseconds' | 'humanize' | 'humanizePrecise';
|
||||
|
||||
export interface FieldFormatParams {
|
||||
export interface FieldFormatParams extends BaseFieldFormatParams {
|
||||
inputFormat?: InputFormat;
|
||||
outputFormat?: OutputFormat;
|
||||
outputPrecision?: number;
|
||||
|
@ -135,10 +138,7 @@ export interface FieldFormatParams {
|
|||
|
||||
export interface FieldFormat {
|
||||
field: string;
|
||||
format: {
|
||||
id: FormatType;
|
||||
params: FieldFormatParams;
|
||||
};
|
||||
format: SerializedFieldFormat<FieldFormatParams>;
|
||||
}
|
||||
|
||||
export interface BuilderItem {
|
||||
|
|
|
@ -65,15 +65,15 @@ const getAppDataViewId = (app: AppDataType, indices: string) => {
|
|||
return `${dataViewList?.[app] ?? app}_${postfix}`;
|
||||
};
|
||||
|
||||
export function isParamsSame(param1: IFieldFormat['_params'], param2: FieldFormatParams) {
|
||||
export function isParamsSame(param1: IFieldFormat['_params'], param2?: FieldFormatParams) {
|
||||
const isSame =
|
||||
param1?.inputFormat === param2?.inputFormat &&
|
||||
param1?.outputFormat === param2?.outputFormat &&
|
||||
param1?.useShortSuffix === param2?.useShortSuffix &&
|
||||
param1?.showSuffix === param2?.showSuffix;
|
||||
|
||||
if (param2.outputPrecision !== undefined) {
|
||||
return param2?.outputPrecision === param1?.outputPrecision && isSame;
|
||||
if (param2?.outputPrecision !== undefined) {
|
||||
return param2.outputPrecision === param1?.outputPrecision && isSame;
|
||||
}
|
||||
|
||||
return isSame;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue