Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Lens] Add new Metric formatter migrations #159539

Merged
merged 10 commits into from
Jun 15, 2023
Original file line number Diff line number Diff line change
Expand Up @@ -66,11 +66,11 @@ describe('checking migration metadata changes on all registered SO types', () =>
"app_search_telemetry": "36234f19573ad397ac30197c45ac219921cc3106",
"application_usage_daily": "20142d23fe5d05ba22b4bc46614d99883bc488f0",
"application_usage_totals": "a29ab014edc20382b9ce22ede221b18cee5d93a6",
"canvas-element": "b39dfe54b9ff3ecc4c6bc5bed6a14b0a0fe83644",
"canvas-workpad": "4df66cf25eba8e7e25c061a1b2a5aadbb1f436e9",
"canvas-workpad-template": "52a35f737b579a570510fca361fddd158d2a92ad",
"canvas-element": "cdedc2123eb8a1506b87a56b0bcce60f4ec08bc8",
"canvas-workpad": "9d82aafb19586b119e5c9382f938abe28c26ca5c",
"canvas-workpad-template": "c077b0087346776bb3542b51e1385d172cb24179",
"cases": "b43a8ce985c406167e1d115381805a48cb3b0e61",
"cases-comments": "ded400d82c5ea26959c2ee8e54896981d499a226",
"cases-comments": "5cb0a421588831c2a950e50f486048b8aabbae25",
"cases-configure": "44ed7b8e0f44df39516b8870589b89e32224d2bf",
"cases-connector-mappings": "f9d1ac57e484e69506c36a8051e4d61f4a8cfd25",
"cases-telemetry": "f219eb7e26772884342487fc9602cfea07b3cedc",
Expand All @@ -80,7 +80,7 @@ describe('checking migration metadata changes on all registered SO types', () =>
"connector_token": "5a9ac29fe9c740eb114e9c40517245c71706b005",
"core-usage-stats": "b3c04da317c957741ebcdedfea4524049fdc79ff",
"csp-rule-template": "c151324d5f85178169395eecb12bac6b96064654",
"dashboard": "1635368413415b340ae6f43fcd0a55c5dcdd4f41",
"dashboard": "0611794ce10d25a36da0770c91376c575e92e8f2",
"endpoint:user-artifact-manifest": "1c3533161811a58772e30cdc77bac4631da3ef2b",
"enterprise_search_telemetry": "9ac912e1417fc8681e0cd383775382117c9e3d3d",
"epm-packages": "2449bb565f987eff70b1b39578bb17e90c404c6e",
Expand Down Expand Up @@ -111,7 +111,7 @@ describe('checking migration metadata changes on all registered SO types', () =>
"inventory-view": "b8683c8e352a286b4aca1ab21003115a4800af83",
"kql-telemetry": "93c1d16c1a0dfca9c8842062cf5ef8f62ae401ad",
"legacy-url-alias": "9b8cca3fbb2da46fd12823d3cd38fdf1c9f24bc8",
"lens": "fd6a7938f41888e5ee499fcc5e749489981393aa",
"lens": "5cfa2c52b979b4f8df56dd13c477e152183468b9",
"lens-ui-telemetry": "8c47a9e393861f76e268345ecbadfc8a5fb1e0bd",
"maintenance-window": "d893544460abad56ff7a0e25b78f78776dfe10d1",
"map": "76c71023bd198fb6b1163b31bafd926fe2ceb9da",
Expand Down
4 changes: 2 additions & 2 deletions test/api_integration/apis/saved_objects/bulk_get.ts
Original file line number Diff line number Diff line change
Expand Up @@ -230,10 +230,10 @@ export default function ({ getService }: FtrProviderContext) {
type: 'dashboard',
namespaces: ['default'],
migrationVersion: {
dashboard: '8.7.0',
dashboard: '8.9.0',
},
coreMigrationVersion: '8.8.0',
typeMigrationVersion: '8.7.0',
typeMigrationVersion: '8.9.0',
updated_at: '2015-01-01T00:00:00.000Z',
created_at: '2015-01-01T00:00:00.000Z',
version: resp.body.saved_objects[3].version,
Expand Down
4 changes: 2 additions & 2 deletions test/api_integration/apis/saved_objects/get.ts
Original file line number Diff line number Diff line change
Expand Up @@ -80,10 +80,10 @@ export default function ({ getService }: FtrProviderContext) {
type: 'dashboard',
namespaces: ['default'],
migrationVersion: {
dashboard: '8.7.0',
dashboard: '8.9.0',
},
coreMigrationVersion: '8.8.0',
typeMigrationVersion: '8.7.0',
typeMigrationVersion: '8.9.0',
updated_at: resp.body.updated_at,
created_at: resp.body.created_at,
version: resp.body.version,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ import {
commonMigratePartitionChartGroups,
commonMigratePartitionMetrics,
commonMigrateIndexPatternDatasource,
commonMigrateMetricFormatter,
} from '../migrations/common_migrations';
import {
CustomVisualizationMigrations,
Expand All @@ -42,6 +43,7 @@ import {
LensDocShape810,
LensDocShape850,
LensDocShapePre712,
LensDocShape860,
VisState716,
VisState810,
VisState850,
Expand Down Expand Up @@ -168,6 +170,13 @@ export const makeLensEmbeddableFactory =
attributes: migratedLensState,
} as unknown as SerializableRecord;
},
'8.9.0': (state) => {
const lensState = state as unknown as SavedObject<LensDocShape860>;
return {
...lensState,
attributes: commonMigrateMetricFormatter(lensState.attributes),
} as unknown as SerializableRecord;
},
// FOLLOW THESE GUIDELINES IF YOU ARE ADDING A NEW MIGRATION!
// 1. Make sure you are applying migrations for a given version in the same order here as they are applied in x-pack/plugins/lens/server/migrations/saved_object_migrations.ts
}),
Expand Down
93 changes: 92 additions & 1 deletion x-pack/plugins/lens/server/migrations/common_migrations.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,9 @@ import {
getLensDataViewMigrations,
getLensFilterMigrations,
commonMigratePartitionChartGroups,
commonMigrateMetricFormatter,
} from './common_migrations';
import { LensDocShape840 } from './types';
import { LensDocShape840, LensDocShape860 } from './types';

describe('Lens migrations', () => {
describe('applying filter migrations', () => {
Expand Down Expand Up @@ -169,4 +170,94 @@ describe('Lens migrations', () => {
`);
});
});

describe('migrate new metric formatters to uniform configuration', () => {
function createVisualizationSO(
type: string,
lensFormatId: undefined | string,
bucketed: boolean = false
): { attributes: LensDocShape860<unknown> } {
return {
attributes: {
filters: [],
visualizationType: type,
title: '',
expression: '',
state: {
datasourceMetaData: { filterableIndexPatterns: [] },
visualization: {},
filters: [],
query: { query: '', language: 'kuery' },
datasourceStates: {
formBased: {
currentIndexPatternId: '',
layers: {
test: {
columnOrder: [],
columns: {
col1: {
operationType: 'test',
isBucketed: bucketed,
params: {
...(lensFormatId ? { format: { id: lensFormatId } } : {}),
},
},
},
},
},
},
},
},
},
};
}

it('should not apply the migration non-metric visualization types', () => {
const lensFormatId = 'number';
const lensVisualizationSavedObject = createVisualizationSO('lnsXY', lensFormatId);
const migratedColumn = commonMigrateMetricFormatter(lensVisualizationSavedObject.attributes)
.state.datasourceStates.formBased.layers.test.columns.col1;

expect(migratedColumn.params).toEqual({ format: { id: lensFormatId } });
});

it.each`
lensFormat | bucketed | expectedCompact
${'default'} | ${true} | ${false}
${'number'} | ${true} | ${false}
${'number'} | ${false} | ${true}
${'percentage'} | ${false} | ${true}
${'bytes'} | ${false} | ${false}
${'bits'} | ${false} | ${false}
${'default'} | ${false} | ${false}
`(
'should migrate lens column (bucketed: $bucketed) format configuration "$lensFormat" into new explicit formatter (compact: $expectedCompact)',
({ lensFormat, bucketed, expectedCompact }) => {
const lensFormatId = lensFormat === 'default' ? undefined : lensFormat;
const lensVisualizationSavedObject = createVisualizationSO(
'lnsMetric',
lensFormatId,
bucketed
);

const migratedColumn = commonMigrateMetricFormatter(lensVisualizationSavedObject.attributes)
.state.datasourceStates.formBased.layers.test.columns.col1;

if (bucketed) {
expect(migratedColumn.params).toEqual(
lensFormatId ? { format: { id: lensFormatId } } : {}
);
}
if (!lensFormatId) {
expect(migratedColumn.params).toEqual({});
} else if (bucketed || !expectedCompact) {
expect(migratedColumn.params).toEqual({ format: { id: lensFormatId } });
} else {
expect(migratedColumn.params).toEqual({
format: { id: lensFormatId, params: { compact: true } },
});
}
}
);
});
});
67 changes: 67 additions & 0 deletions x-pack/plugins/lens/server/migrations/common_migrations.ts
Original file line number Diff line number Diff line change
Expand Up @@ -571,3 +571,70 @@ export const commonMigratePartitionMetrics = (attributes: LensDocShape860<unknow
layers: Array<{ metrics: string[] }>;
}>;
};

export const commonMigrateMetricFormatter = (attributes: LensDocShape860<unknown>) => {
if (attributes.visualizationType !== 'lnsMetric') {
return attributes as LensDocShape860<unknown>;
}
if (!attributes.state.datasourceStates.formBased) {
return attributes as LensDocShape860<unknown>;
}

type LayersType = LensDocShape860['state']['datasourceStates']['formBased']['layers'];

const updatedLayersWithCompactFormatters: LayersType = {};
for (const [layerId, layer] of Object.entries(
attributes.state.datasourceStates.formBased.layers
)) {
const newColumns: Record<string, Record<string, unknown>> = {};
for (const [id, column] of Object.entries(layer.columns)) {
const params = column.params as {
format?: { id: string; params: Record<string, string | boolean> };
};
if (column.isBucketed) {
newColumns[id] = column;
} else {
// When value formatting is set to Default, assume nothing
// Bytes and bits are already compact
if (!params?.format || ['bytes', 'bits'].includes(params.format.id)) {
newColumns[id] = column;
} else {
// Metric only support numeric values
// suffix is not taken into account as it wasn't possible in metric visualization before this version
newColumns[id] = {
...column,
params: {
...params,
format: {
...params?.format,
id: params?.format.id || 'number',
params: {
...params?.format?.params,
compact: true,
},
},
},
};
}
}
}
updatedLayersWithCompactFormatters[layerId] = {
...layer,
columns: newColumns,
};
}

return {
...attributes,
state: {
...attributes.state,
datasourceStates: {
...attributes.state.datasourceStates,
formBased: {
...attributes.state.datasourceStates.formBased,
layers: updatedLayersWithCompactFormatters,
},
},
},
};
};
Original file line number Diff line number Diff line change
Expand Up @@ -2537,4 +2537,5 @@ describe('Lens migrations', () => {
);
});
});
// For 8.8.0 tests are already executed at unit level in common_migrations
});
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ import {
commonMigratePartitionChartGroups,
commonMigratePartitionMetrics,
commonMigrateIndexPatternDatasource,
commonMigrateMetricFormatter,
} from './common_migrations';

interface LensDocShapePre710<VisualizationState = unknown> {
Expand Down Expand Up @@ -562,6 +563,11 @@ const migratePartitionMetrics: SavedObjectMigrationFn<LensDocShape860, LensDocSh
attributes: commonMigratePartitionMetrics(doc.attributes),
});

const migrateMetricFormatter: SavedObjectMigrationFn<LensDocShape860, LensDocShape860> = (doc) => ({
...doc,
attributes: commonMigrateMetricFormatter(doc.attributes),
});

const lensMigrations: SavedObjectMigrationMap = {
'7.7.0': removeInvalidAccessors,
// The order of these migrations matter, since the timefield migration relies on the aggConfigs
Expand All @@ -584,6 +590,7 @@ const lensMigrations: SavedObjectMigrationMap = {
'8.3.0': flow(lockOldMetricVisSettings, preserveOldLegendSizeDefault, fixValueLabelsInXY),
'8.5.0': flow(migrateMetricIds, enrichAnnotationLayers, migratePartitionChartGroups),
'8.6.0': flow(migrateIndexPatternDatasource, migratePartitionMetrics),
'8.9.0': migrateMetricFormatter,
// FOLLOW THESE GUIDELINES IF YOU ARE ADDING A NEW MIGRATION!
// 1. Make sure you are applying migrations for a given version in the same order here as they are applied in x-pack/plugins/lens/server/embeddable/make_lens_embeddable_factory.ts
};
Expand Down