diff --git a/src/platform/plugins/shared/discover/common/embeddable/get_transform_in.ts b/src/platform/plugins/shared/discover/common/embeddable/get_transform_in.ts index bac4daa26e39c..ff66dce2fd9b9 100644 --- a/src/platform/plugins/shared/discover/common/embeddable/get_transform_in.ts +++ b/src/platform/plugins/shared/discover/common/embeddable/get_transform_in.ts @@ -7,15 +7,16 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ +import { omit } from 'lodash'; import { SavedSearchType } from '@kbn/saved-search-plugin/common'; import type { SavedObjectReference } from '@kbn/core/server'; +import { extractReferences, parseSearchSourceJSON } from '@kbn/data-plugin/common'; import type { DrilldownTransforms } from '@kbn/embeddable-plugin/common'; import type { SearchEmbeddableByReferenceState, SearchEmbeddableState, StoredSearchEmbeddableState, } from './types'; -import { extract } from './search_inject_extract'; export const SAVED_SEARCH_SAVED_OBJECT_REF_NAME = 'savedObjectRef'; @@ -47,22 +48,38 @@ export function getTransformIn(transformDrilldownsIn: DrilldownTransforms['trans } // by value - const { state: extractedState, references } = extract({ - type: SavedSearchType, - attributes: storedState.attributes, + const tabReferences: SavedObjectReference[] = []; + const tabs = storedState.attributes.tabs.map((tab) => { + try { + const searchSourceValues = parseSearchSourceJSON( + tab.attributes.kibanaSavedObjectMeta.searchSourceJSON + ); + const [searchSourceFields, searchSourceReferences] = extractReferences(searchSourceValues); + tabReferences.push(...searchSourceReferences); + return { + ...tab, + attributes: { + ...tab.attributes, + kibanaSavedObjectMeta: { + ...tab.attributes.kibanaSavedObjectMeta, + searchSourceJSON: JSON.stringify(searchSourceFields), + }, + }, + }; + } catch (e) { + return tab; + } }); return { state: { ...storedState, attributes: { - ...storedState.attributes, - ...extractedState.attributes, - // discover session stores references as part of attributes - references, + ...omit(storedState.attributes, 'references'), + tabs, }, }, - references: [...references, ...drilldownReferences], + references: [...tabReferences, ...drilldownReferences], }; } return transformIn; diff --git a/src/platform/plugins/shared/discover/common/embeddable/get_transform_out.ts b/src/platform/plugins/shared/discover/common/embeddable/get_transform_out.ts index 932dea7c1aef0..96f94d5f94dc1 100644 --- a/src/platform/plugins/shared/discover/common/embeddable/get_transform_out.ts +++ b/src/platform/plugins/shared/discover/common/embeddable/get_transform_out.ts @@ -7,18 +7,18 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ +import { flow, omit } from 'lodash'; import { extractTabs, SavedSearchType } from '@kbn/saved-search-plugin/common'; +import { injectReferences, parseSearchSourceJSON } from '@kbn/data-plugin/common'; import type { DrilldownTransforms } from '@kbn/embeddable-plugin/common'; import type { SavedObjectReference } from '@kbn/core/server'; import { transformTitlesOut } from '@kbn/presentation-publishing'; -import { flow } from 'lodash'; import type { SearchEmbeddableByReferenceState, SearchEmbeddableByValueState, StoredSearchEmbeddableByValueState, StoredSearchEmbeddableState, } from './types'; -import { inject } from './search_inject_extract'; import { SAVED_SEARCH_SAVED_OBJECT_REF_NAME } from './get_transform_in'; function isByValue( @@ -42,14 +42,34 @@ export function getTransformOut(transformDrilldownsOut: DrilldownTransforms['tra const state = transformsFlow(storedState); if (isByValue(state)) { - const tabsState = { - ...state, - attributes: extractTabs(state.attributes), - }; - const { attributes } = inject({ type: SavedSearchType, ...tabsState }, references ?? []); + const tabsState = { ...state, attributes: extractTabs(state.attributes) }; + const tabs = tabsState.attributes.tabs.map((tab) => { + try { + const searchSourceValues = parseSearchSourceJSON( + tab.attributes.kibanaSavedObjectMeta.searchSourceJSON + ); + const searchSourceFields = injectReferences(searchSourceValues, references ?? []); + return { + ...tab, + attributes: { + ...omit(tab.attributes, 'references'), + kibanaSavedObjectMeta: { + ...tab.attributes.kibanaSavedObjectMeta, + searchSourceJSON: JSON.stringify(searchSourceFields), + }, + }, + }; + } catch (e) { + return tab; + } + }); + return { ...state, - attributes, + attributes: { + ...state.attributes, + tabs, + }, } as SearchEmbeddableByValueState; } diff --git a/src/platform/plugins/shared/discover/common/embeddable/index.ts b/src/platform/plugins/shared/discover/common/embeddable/index.ts index 9e2055fcf02b9..b383982938a5c 100644 --- a/src/platform/plugins/shared/discover/common/embeddable/index.ts +++ b/src/platform/plugins/shared/discover/common/embeddable/index.ts @@ -7,5 +7,4 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -export { inject, extract } from './search_inject_extract'; export { getSearchEmbeddableTransforms } from './search_embeddable_transforms'; diff --git a/src/platform/plugins/shared/discover/common/embeddable/search_embeddable_transforms.test.ts b/src/platform/plugins/shared/discover/common/embeddable/search_embeddable_transforms.test.ts index ca15bb6b3afda..78140e4f0bca6 100644 --- a/src/platform/plugins/shared/discover/common/embeddable/search_embeddable_transforms.test.ts +++ b/src/platform/plugins/shared/discover/common/embeddable/search_embeddable_transforms.test.ts @@ -9,7 +9,6 @@ import type { DrilldownTransforms } from '@kbn/embeddable-plugin/common'; import { getSearchEmbeddableTransforms } from './search_embeddable_transforms'; -import { extract, inject } from './search_inject_extract'; import type { SearchEmbeddableByValueState, StoredSearchEmbeddableByValueState, @@ -18,13 +17,6 @@ import type { SearchEmbeddableState, } from './types'; -jest.mock('./search_inject_extract', () => { - return { - inject: jest.fn((state, references) => state), - extract: jest.fn((state) => ({ state, references: [] })), - }; -}); - const mockDrilldownTransforms = { transformIn: jest.fn().mockImplementation((state: SearchEmbeddableState) => ({ state, @@ -82,10 +74,6 @@ describe('searchEmbeddableTransforms', () => { state, references ); - expect(inject).toHaveBeenCalledWith( - { type: 'search', ...{ ...state, attributes: expectedAttributes } }, - references - ); expect(result).toEqual({ ...state, attributes: expectedAttributes, @@ -204,7 +192,6 @@ describe('searchEmbeddableTransforms', () => { searchSourceJSON: '{"query":{"match_all":{}}}', }, tabs: [], - references: [], }, title: 'Panel Title', }; @@ -212,10 +199,6 @@ describe('searchEmbeddableTransforms', () => { const result = getSearchEmbeddableTransforms(mockDrilldownTransforms).transformIn!(serializedState); - expect(extract).toHaveBeenCalledWith({ - type: 'search', - attributes: serializedState.attributes, - }); expect(result.state as StoredSearchEmbeddableByValueState).toEqual(serializedState); expect(result.references).toEqual([]); }); @@ -244,10 +227,6 @@ describe('searchEmbeddableTransforms', () => { expect(result.references).toEqual([]); expect(mockDrilldownTransforms.transformIn).toHaveBeenCalledWith(serializedState); - expect(extract).toHaveBeenCalledWith({ - type: 'search', - attributes: serializedState.attributes, - }); }); }); }); diff --git a/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.test.ts b/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.test.ts deleted file mode 100644 index aa0af9b0394f3..0000000000000 --- a/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.test.ts +++ /dev/null @@ -1,78 +0,0 @@ -/* - * 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", the "GNU Affero General Public License v3.0 only", 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", the "GNU Affero General Public - * License v3.0 only", or the "Server Side Public License, v 1". - */ - -import type { SavedSearchByValueAttributes } from '@kbn/saved-search-plugin/common'; -import { extract, inject } from './search_inject_extract'; - -describe('search inject extract', () => { - describe('inject', () => { - it('should not inject references if state does not have attributes', () => { - const state = { type: 'type', id: 'id' }; - const injectedReferences = [{ name: 'name', type: 'type', id: 'id' }]; - expect(inject(state, injectedReferences)).toEqual(state); - }); - - it('should inject references if state has references with the same name', () => { - const state = { - type: 'type', - id: 'id', - attributes: { - references: [{ name: 'name', type: 'type', id: '1' }], - }, - }; - const injectedReferences = [{ name: 'name', type: 'type', id: '2' }]; - expect(inject(state, injectedReferences)).toEqual({ - ...state, - attributes: { - ...state.attributes, - references: injectedReferences, - }, - }); - }); - - it('should clear references if state has no references with the same name', () => { - const state = { - type: 'type', - id: 'id', - attributes: { - references: [{ name: 'name', type: 'type', id: '1' }], - }, - }; - const injectedReferences = [{ name: 'other', type: 'type', id: '2' }]; - expect(inject(state, injectedReferences)).toEqual({ - ...state, - attributes: { - ...state.attributes, - references: [], - }, - }); - }); - }); - - describe('extract', () => { - it('should not extract references if state does not have attributes', () => { - const state = { type: 'type', id: 'id' }; - expect(extract(state)).toEqual({ state, references: [] }); - }); - - it('should extract references if state has references', () => { - const state = { - type: 'type', - id: 'id', - attributes: { - references: [{ name: 'name', type: 'type', id: '1' }], - } as SavedSearchByValueAttributes, - }; - expect(extract(state)).toEqual({ - state, - references: [{ name: 'name', type: 'type', id: '1' }], - }); - }); - }); -}); diff --git a/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.ts b/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.ts deleted file mode 100644 index b3ce3529a3585..0000000000000 --- a/src/platform/plugins/shared/discover/common/embeddable/search_inject_extract.ts +++ /dev/null @@ -1,62 +0,0 @@ -/* - * 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", the "GNU Affero General Public License v3.0 only", 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", the "GNU Affero General Public - * License v3.0 only", or the "Server Side Public License, v 1". - */ - -import type { WithRequiredProperty } from '@kbn/utility-types'; -import type { SavedObjectReference } from '@kbn/core-saved-objects-server'; -import type { EmbeddableStateWithType } from '@kbn/embeddable-plugin/common'; -import type { SavedSearchByValueAttributes } from '@kbn/saved-search-plugin/common'; - -type EmbeddableStateWithTypeAndAttributes = EmbeddableStateWithType & { - attributes?: SavedSearchByValueAttributes; -}; - -export const inject = ( - state: EmbeddableStateWithType, - injectedReferences: SavedObjectReference[] -): EmbeddableStateWithTypeAndAttributes => { - if (hasAttributes(state)) { - // Filter out references that are not in the state - // https://github.com/elastic/kibana/pull/119079 - const references = state.attributes.references - .map((stateRef) => - injectedReferences.find((injectedRef) => injectedRef.name === stateRef.name) - ) - .filter(Boolean); - - state = { - ...state, - attributes: { - ...state.attributes, - references, - }, - } as EmbeddableStateWithTypeAndAttributes; - } - - return state; -}; - -export const extract = ( - state: EmbeddableStateWithTypeAndAttributes -): { - state: EmbeddableStateWithTypeAndAttributes; - references: SavedObjectReference[]; -} => { - let references: SavedObjectReference[] = []; - - if (hasAttributes(state)) { - references = state.attributes.references; - } - - return { state, references }; -}; - -const hasAttributes = ( - state: EmbeddableStateWithType -): state is WithRequiredProperty => - 'attributes' in state; diff --git a/src/platform/plugins/shared/discover/moon.yml b/src/platform/plugins/shared/discover/moon.yml index 1ad1f28cdd481..5c921488e4020 100644 --- a/src/platform/plugins/shared/discover/moon.yml +++ b/src/platform/plugins/shared/discover/moon.yml @@ -64,7 +64,6 @@ dependsOn: - '@kbn/unified-field-list' - '@kbn/cell-actions' - '@kbn/shared-ux-utility' - - '@kbn/core-saved-objects-server' - '@kbn/discover-utils' - '@kbn/search-errors' - '@kbn/search-response-warnings' diff --git a/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.test.ts b/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.test.ts index 7aa15737d5f25..f5ba30a5099f2 100644 --- a/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.test.ts +++ b/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.test.ts @@ -132,10 +132,8 @@ describe('Serialization utils', () => { serializeDynamicActions: jest.fn(), }); - const attributes = toSavedSearchAttributes( - savedSearch, - searchSource.serialize().searchSourceJSON - ); + const searchSourceJSON = JSON.stringify(searchSource.getSerializedFields()); + const attributes = toSavedSearchAttributes(savedSearch, searchSourceJSON); expect(serializedState).toEqual({ attributes: { @@ -146,7 +144,6 @@ describe('Serialization utils', () => { id: expect.any(String), }, ], - references: mockedSavedSearchAttributes.references, }, }); }); diff --git a/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.ts b/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.ts index 38d7953325d5f..fd6b5b414f8c6 100644 --- a/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.ts +++ b/src/platform/plugins/shared/discover/public/embeddable/utils/serialization_utils.ts @@ -85,7 +85,7 @@ export const serializeState = ({ savedObjectId?: string; }): SearchEmbeddableState => { const searchSource = savedSearch.searchSource; - const { searchSourceJSON, references: originalReferences } = searchSource.serialize(); + const searchSourceJSON = JSON.stringify(searchSource.getSerializedFields()); const savedSearchAttributes = toSavedSearchAttributes(savedSearch, searchSourceJSON); if (savedObjectId) { @@ -110,17 +110,10 @@ export const serializeState = ({ }; } - const state = { - attributes: { - ...savedSearchAttributes, - references: originalReferences, - }, - }; - return { ...serializeTitles(), ...serializeTimeRange(), ...serializeDynamicActions?.(), - ...state, + attributes: savedSearchAttributes, }; }; diff --git a/src/platform/plugins/shared/discover/server/embeddable/search_embeddable_factory.ts b/src/platform/plugins/shared/discover/server/embeddable/search_embeddable_factory.ts index 4a93f87b39954..f4beb0df760c1 100644 --- a/src/platform/plugins/shared/discover/server/embeddable/search_embeddable_factory.ts +++ b/src/platform/plugins/shared/discover/server/embeddable/search_embeddable_factory.ts @@ -9,10 +9,7 @@ import type { EmbeddableRegistryDefinition } from '@kbn/embeddable-plugin/server'; import { SEARCH_EMBEDDABLE_TYPE } from '@kbn/discover-utils'; -import { inject, extract } from '../../common/embeddable'; export const createSearchEmbeddableFactory = (): EmbeddableRegistryDefinition => ({ id: SEARCH_EMBEDDABLE_TYPE, - inject, - extract, }); diff --git a/src/platform/plugins/shared/discover/tsconfig.json b/src/platform/plugins/shared/discover/tsconfig.json index 1e04653fbf535..8eae07f516f83 100644 --- a/src/platform/plugins/shared/discover/tsconfig.json +++ b/src/platform/plugins/shared/discover/tsconfig.json @@ -57,7 +57,6 @@ "@kbn/unified-field-list", "@kbn/cell-actions", "@kbn/shared-ux-utility", - "@kbn/core-saved-objects-server", "@kbn/discover-utils", "@kbn/search-errors", "@kbn/search-response-warnings", diff --git a/src/platform/plugins/shared/saved_search/common/types.ts b/src/platform/plugins/shared/saved_search/common/types.ts index 190661ce2f092..ca85f572f54c6 100644 --- a/src/platform/plugins/shared/saved_search/common/types.ts +++ b/src/platform/plugins/shared/saved_search/common/types.ts @@ -77,7 +77,8 @@ export interface SavedSearchAttributes { } export type SavedSearchByValueAttributes = SavedSearchAttributes & { - references: Reference[]; + /** @deprecated References are now extracted/injected by server transforms */ + references?: Reference[]; }; /** @internal **/ diff --git a/src/platform/plugins/shared/saved_search/public/service/to_saved_search.ts b/src/platform/plugins/shared/saved_search/public/service/to_saved_search.ts index 9844e6eb55a70..7f6338115535e 100644 --- a/src/platform/plugins/shared/saved_search/public/service/to_saved_search.ts +++ b/src/platform/plugins/shared/saved_search/public/service/to_saved_search.ts @@ -32,10 +32,11 @@ export const byValueToSavedSearch = async < serializable?: Serialized ): Promise => { const { sharingSavedObjectProps, managed } = result.metaInfo ?? {}; - + const { references, ...attributes } = result.attributes; return await convertToSavedSearch( { - ...splitReferences(result.attributes), + attributes, + references: references ?? [], savedSearchId: undefined, sharingSavedObjectProps, managed, @@ -44,15 +45,3 @@ export const byValueToSavedSearch = async < serializable ); }; - -const splitReferences = (attributes: SavedSearchByValueAttributes) => { - const { references, ...attrs } = attributes; - - return { - references, - attributes: { - ...attrs, - description: attrs.description ?? '', - }, - }; -};