diff --git a/src/plugins/controls/common/constants.ts b/src/plugins/controls/common/constants.ts index e100474177c71..e375a7b2315bc 100644 --- a/src/plugins/controls/common/constants.ts +++ b/src/plugins/controls/common/constants.ts @@ -7,11 +7,11 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { ControlStyle, ControlWidth } from './types'; +import { ControlLabelPosition, ControlWidth } from './types'; export const DEFAULT_CONTROL_WIDTH: ControlWidth = 'medium'; export const DEFAULT_CONTROL_GROW: boolean = true; -export const DEFAULT_CONTROL_STYLE: ControlStyle = 'oneLine'; +export const DEFAULT_CONTROL_LABEL_POSITION: ControlLabelPosition = 'oneLine'; export const TIME_SLIDER_CONTROL = 'timeSlider'; export const RANGE_SLIDER_CONTROL = 'rangeSliderControl'; diff --git a/src/plugins/controls/common/control_group/types.ts b/src/plugins/controls/common/control_group/types.ts index cb51cf79e5400..eb47d8b13eb79 100644 --- a/src/plugins/controls/common/control_group/types.ts +++ b/src/plugins/controls/common/control_group/types.ts @@ -8,7 +8,7 @@ */ import { DataViewField } from '@kbn/data-views-plugin/common'; -import { ControlStyle, DefaultControlState, ParentIgnoreSettings } from '../types'; +import { ControlLabelPosition, DefaultControlState, ParentIgnoreSettings } from '../types'; export const CONTROL_GROUP_TYPE = 'control_group'; @@ -31,7 +31,7 @@ export interface ControlGroupEditorConfig { export interface ControlGroupRuntimeState { chainingSystem: ControlGroupChainingSystem; - labelPosition: ControlStyle; // TODO: Rename this type to ControlLabelPosition + labelPosition: ControlLabelPosition; autoApplySelections: boolean; ignoreParentSettings?: ParentIgnoreSettings; @@ -50,7 +50,7 @@ export interface ControlGroupSerializedState ignoreParentSettingsJSON: string; // In runtime state, we refer to this property as `labelPosition`; // to avoid migrations, we will continue to refer to this property as `controlStyle` in the serialized state - controlStyle: ControlStyle; + controlStyle: ControlLabelPosition; // In runtime state, we refer to the inverse of this property as `autoApplySelections` // to avoid migrations, we will continue to refer to this property as `showApplySelections` in the serialized state showApplySelections?: boolean; diff --git a/src/plugins/controls/common/index.ts b/src/plugins/controls/common/index.ts index c59e4c04ac1b0..dd9c56778bb68 100644 --- a/src/plugins/controls/common/index.ts +++ b/src/plugins/controls/common/index.ts @@ -8,7 +8,7 @@ */ export type { - ControlStyle, + ControlLabelPosition, ControlWidth, DefaultControlState, DefaultDataControlState, @@ -18,7 +18,7 @@ export type { export { DEFAULT_CONTROL_GROW, - DEFAULT_CONTROL_STYLE, + DEFAULT_CONTROL_LABEL_POSITION, DEFAULT_CONTROL_WIDTH, OPTIONS_LIST_CONTROL, RANGE_SLIDER_CONTROL, diff --git a/src/plugins/controls/common/options_list/types.ts b/src/plugins/controls/common/options_list/types.ts index e5eccbcab5cf5..10d4a88553586 100644 --- a/src/plugins/controls/common/options_list/types.ts +++ b/src/plugins/controls/common/options_list/types.ts @@ -15,8 +15,6 @@ import { OptionsListSortingType } from './suggestions_sorting'; import { DefaultDataControlState } from '../types'; import { OptionsListSearchTechnique } from './suggestions_searching'; -export const OPTIONS_LIST_CONTROL = 'optionsListControl'; // TODO: Replace with OPTIONS_LIST_CONTROL_TYPE - /** * ---------------------------------------------------------------- * Options list state types diff --git a/src/plugins/controls/common/types.ts b/src/plugins/controls/common/types.ts index 34d4708b3e991..d3a6261aeb9da 100644 --- a/src/plugins/controls/common/types.ts +++ b/src/plugins/controls/common/types.ts @@ -8,7 +8,7 @@ */ export type ControlWidth = 'small' | 'medium' | 'large'; -export type ControlStyle = 'twoLine' | 'oneLine'; +export type ControlLabelPosition = 'twoLine' | 'oneLine'; export type TimeSlice = [number, number]; diff --git a/src/plugins/controls/jest_setup.ts b/src/plugins/controls/jest_setup.ts index 722f87562328e..04a52e3b6653f 100644 --- a/src/plugins/controls/jest_setup.ts +++ b/src/plugins/controls/jest_setup.ts @@ -8,8 +8,5 @@ */ // Start the services with stubs -import { pluginServices } from './public/services'; -import { registry } from './public/services/plugin_services.stub'; - -registry.start({}); -pluginServices.setRegistry(registry); +import { setStubKibanaServices } from './public/services/mocks'; +setStubKibanaServices(); diff --git a/src/plugins/controls/kibana.jsonc b/src/plugins/controls/kibana.jsonc index bd65ecc2d0b6f..add8c14ee3391 100644 --- a/src/plugins/controls/kibana.jsonc +++ b/src/plugins/controls/kibana.jsonc @@ -9,8 +9,6 @@ "browser": true, "requiredPlugins": [ "presentationUtil", - "kibanaReact", - "expressions", "embeddable", "dataViews", "data", @@ -18,6 +16,6 @@ "uiActions" ], "extraPublicDirs": ["common"], - "requiredBundles": ["kibanaUtils"] + "requiredBundles": [] } } diff --git a/src/plugins/controls/public/actions/clear_control_action.tsx b/src/plugins/controls/public/actions/clear_control_action.tsx index b7c2777473fd5..02347ace2fd8d 100644 --- a/src/plugins/controls/public/actions/clear_control_action.tsx +++ b/src/plugins/controls/public/actions/clear_control_action.tsx @@ -11,42 +11,10 @@ import React, { SyntheticEvent } from 'react'; import { EuiButtonIcon, EuiToolTip } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; -import { - apiIsPresentationContainer, - type PresentationContainer, -} from '@kbn/presentation-containers'; -import { - apiCanAccessViewMode, - apiHasParentApi, - apiHasType, - apiHasUniqueId, - apiIsOfType, - type EmbeddableApiContext, - type HasParentApi, - type HasType, - type HasUniqueId, -} from '@kbn/presentation-publishing'; -import { type Action, IncompatibleActionError } from '@kbn/ui-actions-plugin/public'; +import type { EmbeddableApiContext, HasUniqueId } from '@kbn/presentation-publishing'; +import { IncompatibleActionError, type Action } from '@kbn/ui-actions-plugin/public'; import { ACTION_CLEAR_CONTROL } from '.'; -import { CONTROL_GROUP_TYPE } from '..'; -import { isClearableControl, type CanClearSelections } from '../types'; - -export type ClearControlActionApi = HasType & - HasUniqueId & - CanClearSelections & - HasParentApi; - -const isApiCompatible = (api: unknown | null): api is ClearControlActionApi => - Boolean( - apiHasType(api) && - apiHasUniqueId(api) && - isClearableControl(api) && - apiHasParentApi(api) && - apiCanAccessViewMode(api.parentApi) && - apiIsOfType(api.parentApi, CONTROL_GROUP_TYPE) && - apiIsPresentationContainer(api.parentApi) - ); export class ClearControlAction implements Action { public readonly type = ACTION_CLEAR_CONTROL; @@ -56,12 +24,10 @@ export class ClearControlAction implements Action { constructor() {} public readonly MenuItem = ({ context }: { context: EmbeddableApiContext }) => { - if (!isApiCompatible(context.embeddable)) throw new IncompatibleActionError(); - return ( ) => { @@ -75,23 +41,24 @@ export class ClearControlAction implements Action { }; public getDisplayName({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); return i18n.translate('controls.controlGroup.floatingActions.clearTitle', { defaultMessage: 'Clear', }); } public getIconType({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); return 'eraser'; } public async isCompatible({ embeddable }: EmbeddableApiContext) { - return isApiCompatible(embeddable); + const { isCompatible } = await import('./clear_control_action_compatibility_check'); + return isCompatible(embeddable); } public async execute({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); + const { compatibilityCheck } = await import('./clear_control_action_compatibility_check'); + if (!compatibilityCheck(embeddable)) throw new IncompatibleActionError(); + embeddable.clearSelections(); } } diff --git a/src/plugins/controls/public/actions/clear_control_action_compatibility_check.ts b/src/plugins/controls/public/actions/clear_control_action_compatibility_check.ts new file mode 100644 index 0000000000000..f04cb91bc9a3a --- /dev/null +++ b/src/plugins/controls/public/actions/clear_control_action_compatibility_check.ts @@ -0,0 +1,42 @@ +/* + * 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 { PresentationContainer, apiIsPresentationContainer } from '@kbn/presentation-containers'; +import { + HasParentApi, + HasType, + HasUniqueId, + apiCanAccessViewMode, + apiHasParentApi, + apiHasType, + apiHasUniqueId, + apiIsOfType, +} from '@kbn/presentation-publishing'; +import { CONTROL_GROUP_TYPE } from '../../common'; +import { isClearableControl, type CanClearSelections } from '../types'; + +type ClearControlActionApi = HasType & + HasUniqueId & + CanClearSelections & + HasParentApi; + +export const compatibilityCheck = (api: unknown | null): api is ClearControlActionApi => + Boolean( + apiHasType(api) && + apiHasUniqueId(api) && + isClearableControl(api) && + apiHasParentApi(api) && + apiCanAccessViewMode(api.parentApi) && + apiIsOfType(api.parentApi, CONTROL_GROUP_TYPE) && + apiIsPresentationContainer(api.parentApi) + ); + +export function isCompatible(api: unknown) { + return compatibilityCheck(api); +} diff --git a/src/plugins/controls/public/actions/delete_control_action.test.tsx b/src/plugins/controls/public/actions/delete_control_action.test.tsx index 65be8a65ecd6f..c158d743f69ae 100644 --- a/src/plugins/controls/public/actions/delete_control_action.test.tsx +++ b/src/plugins/controls/public/actions/delete_control_action.test.tsx @@ -9,22 +9,15 @@ import { BehaviorSubject } from 'rxjs'; -import { coreMock } from '@kbn/core/public/mocks'; -import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { ViewMode } from '@kbn/presentation-publishing'; - import { getOptionsListControlFactory } from '../react_controls/controls/data_controls/options_list_control/get_options_list_control_factory'; import { OptionsListControlApi } from '../react_controls/controls/data_controls/options_list_control/types'; import { getMockedBuildApi, getMockedControlGroupApi, } from '../react_controls/controls/mocks/control_mocks'; -import { pluginServices } from '../services'; import { DeleteControlAction } from './delete_control_action'; - -const mockDataViews = dataViewPluginMocks.createStartContract(); -const mockCore = coreMock.createStart(); +import { coreServices } from '../services/kibana_services'; const dashboardApi = { viewMode: new BehaviorSubject('view'), @@ -38,11 +31,7 @@ const controlGroupApi = getMockedControlGroupApi(dashboardApi, { let controlApi: OptionsListControlApi; beforeAll(async () => { - const controlFactory = getOptionsListControlFactory({ - core: mockCore, - data: dataPluginMock.createStartContract(), - dataViews: mockDataViews, - }); + const controlFactory = getOptionsListControlFactory(); const uuid = 'testControl'; const control = await controlFactory.buildControl( @@ -72,7 +61,7 @@ test('Execute throws an error when called with an embeddable not in a parent', a describe('Execute should open a confirm modal', () => { test('Canceling modal will keep control', async () => { const spyOn = jest.fn().mockResolvedValue(false); - pluginServices.getServices().overlays.openConfirm = spyOn; + coreServices.overlays.openConfirm = spyOn; const deleteControlAction = new DeleteControlAction(); await deleteControlAction.execute({ embeddable: controlApi }); @@ -83,7 +72,7 @@ describe('Execute should open a confirm modal', () => { test('Confirming modal will delete control', async () => { const spyOn = jest.fn().mockResolvedValue(true); - pluginServices.getServices().overlays.openConfirm = spyOn; + coreServices.overlays.openConfirm = spyOn; const deleteControlAction = new DeleteControlAction(); await deleteControlAction.execute({ embeddable: controlApi }); diff --git a/src/plugins/controls/public/actions/delete_control_action.tsx b/src/plugins/controls/public/actions/delete_control_action.tsx index 45a7a20385627..7ee55ddd3da69 100644 --- a/src/plugins/controls/public/actions/delete_control_action.tsx +++ b/src/plugins/controls/public/actions/delete_control_action.tsx @@ -10,65 +10,25 @@ import React from 'react'; import { EuiButtonIcon, EuiToolTip } from '@elastic/eui'; -import { ViewMode } from '@kbn/embeddable-plugin/public'; import { i18n } from '@kbn/i18n'; -import { - apiIsPresentationContainer, - type PresentationContainer, -} from '@kbn/presentation-containers'; -import { - apiCanAccessViewMode, - apiHasParentApi, - apiHasType, - apiHasUniqueId, - apiIsOfType, - getInheritedViewMode, - type EmbeddableApiContext, - type HasParentApi, - type HasType, - type HasUniqueId, - type PublishesViewMode, -} from '@kbn/presentation-publishing'; +import type { HasUniqueId, EmbeddableApiContext } from '@kbn/presentation-publishing'; import { IncompatibleActionError, type Action } from '@kbn/ui-actions-plugin/public'; import { ACTION_DELETE_CONTROL } from '.'; -import { CONTROL_GROUP_TYPE } from '..'; -import { pluginServices } from '../services'; - -export type DeleteControlActionApi = HasType & - HasUniqueId & - HasParentApi; - -const isApiCompatible = (api: unknown | null): api is DeleteControlActionApi => - Boolean( - apiHasType(api) && - apiHasUniqueId(api) && - apiHasParentApi(api) && - apiCanAccessViewMode(api.parentApi) && - apiIsOfType(api.parentApi, CONTROL_GROUP_TYPE) && - apiIsPresentationContainer(api.parentApi) - ); +import { coreServices } from '../services/kibana_services'; export class DeleteControlAction implements Action { public readonly type = ACTION_DELETE_CONTROL; public readonly id = ACTION_DELETE_CONTROL; public order = 100; // should always be last - private openConfirm; - - constructor() { - ({ - overlays: { openConfirm: this.openConfirm }, - } = pluginServices.getServices()); - } + constructor() {} public readonly MenuItem = ({ context }: { context: EmbeddableApiContext }) => { - if (!isApiCompatible(context.embeddable)) throw new IncompatibleActionError(); - return ( this.execute(context)} @@ -79,46 +39,46 @@ export class DeleteControlAction implements Action { }; public getDisplayName({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); return i18n.translate('controls.controlGroup.floatingActions.removeTitle', { defaultMessage: 'Delete', }); } public getIconType({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); return 'trash'; } public async isCompatible({ embeddable }: EmbeddableApiContext) { - return ( - isApiCompatible(embeddable) && getInheritedViewMode(embeddable.parentApi) === ViewMode.EDIT - ); + const { isCompatible } = await import('./delete_control_action_compatibility_check'); + return isCompatible(embeddable); } public async execute({ embeddable }: EmbeddableApiContext) { - if (!isApiCompatible(embeddable)) throw new IncompatibleActionError(); + const { compatibilityCheck } = await import('./delete_control_action_compatibility_check'); + if (!compatibilityCheck(embeddable)) throw new IncompatibleActionError(); - this.openConfirm( - i18n.translate('controls.controlGroup.management.delete.sub', { - defaultMessage: 'Controls are not recoverable once removed.', - }), - { - confirmButtonText: i18n.translate('controls.controlGroup.management.delete.confirm', { - defaultMessage: 'Delete', - }), - cancelButtonText: i18n.translate('controls.controlGroup.management.delete.cancel', { - defaultMessage: 'Cancel', + coreServices.overlays + .openConfirm( + i18n.translate('controls.controlGroup.management.delete.sub', { + defaultMessage: 'Controls are not recoverable once removed.', }), - title: i18n.translate('controls.controlGroup.management.delete.deleteTitle', { - defaultMessage: 'Delete control?', - }), - buttonColor: 'danger', - } - ).then((confirmed) => { - if (confirmed) { - embeddable.parentApi.removePanel(embeddable.uuid); - } - }); + { + confirmButtonText: i18n.translate('controls.controlGroup.management.delete.confirm', { + defaultMessage: 'Delete', + }), + cancelButtonText: i18n.translate('controls.controlGroup.management.delete.cancel', { + defaultMessage: 'Cancel', + }), + title: i18n.translate('controls.controlGroup.management.delete.deleteTitle', { + defaultMessage: 'Delete control?', + }), + buttonColor: 'danger', + } + ) + .then((confirmed) => { + if (confirmed) { + embeddable.parentApi.removePanel(embeddable.uuid); + } + }); } } diff --git a/src/plugins/controls/public/actions/delete_control_action_compatibility_check.ts b/src/plugins/controls/public/actions/delete_control_action_compatibility_check.ts new file mode 100644 index 0000000000000..a09b3448b2fc1 --- /dev/null +++ b/src/plugins/controls/public/actions/delete_control_action_compatibility_check.ts @@ -0,0 +1,42 @@ +/* + * 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 { ViewMode } from '@kbn/embeddable-plugin/public'; +import { PresentationContainer, apiIsPresentationContainer } from '@kbn/presentation-containers'; +import { + HasParentApi, + HasType, + HasUniqueId, + PublishesViewMode, + apiCanAccessViewMode, + apiHasParentApi, + apiHasType, + apiHasUniqueId, + apiIsOfType, + getInheritedViewMode, +} from '@kbn/presentation-publishing'; +import { CONTROL_GROUP_TYPE } from '../../common'; + +type DeleteControlActionApi = HasType & + HasUniqueId & + HasParentApi; + +export const compatibilityCheck = (api: unknown | null): api is DeleteControlActionApi => + Boolean( + apiHasType(api) && + apiHasUniqueId(api) && + apiHasParentApi(api) && + apiCanAccessViewMode(api.parentApi) && + apiIsOfType(api.parentApi, CONTROL_GROUP_TYPE) && + apiIsPresentationContainer(api.parentApi) + ); + +export function isCompatible(api: unknown) { + return compatibilityCheck(api) && getInheritedViewMode(api.parentApi) === ViewMode.EDIT; +} diff --git a/src/plugins/controls/public/actions/edit_control_action.test.tsx b/src/plugins/controls/public/actions/edit_control_action.test.tsx index 3c28feb907421..b1c24d779aaf6 100644 --- a/src/plugins/controls/public/actions/edit_control_action.test.tsx +++ b/src/plugins/controls/public/actions/edit_control_action.test.tsx @@ -9,9 +9,6 @@ import { BehaviorSubject } from 'rxjs'; -import { coreMock } from '@kbn/core/public/mocks'; -import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import dateMath from '@kbn/datemath'; import type { TimeRange } from '@kbn/es-query'; import type { ViewMode } from '@kbn/presentation-publishing'; @@ -23,12 +20,10 @@ import { getMockedControlGroupApi, } from '../react_controls/controls/mocks/control_mocks'; import { getTimesliderControlFactory } from '../react_controls/controls/timeslider_control/get_timeslider_control_factory'; +import { dataService } from '../services/kibana_services'; import { EditControlAction } from './edit_control_action'; -const mockDataViews = dataViewPluginMocks.createStartContract(); -const mockCore = coreMock.createStart(); -const dataStartServiceMock = dataPluginMock.createStartContract(); -dataStartServiceMock.query.timefilter.timefilter.calculateBounds = (timeRange: TimeRange) => { +dataService.query.timefilter.timefilter.calculateBounds = (timeRange: TimeRange) => { const now = new Date(); return { min: dateMath.parse(timeRange.from, { forceNow: now }), @@ -48,11 +43,7 @@ const controlGroupApi = getMockedControlGroupApi(dashboardApi, { let optionsListApi: OptionsListControlApi; beforeAll(async () => { - const controlFactory = getOptionsListControlFactory({ - core: mockCore, - data: dataStartServiceMock, - dataViews: mockDataViews, - }); + const controlFactory = getOptionsListControlFactory(); const optionsListUuid = 'optionsListControl'; const optionsListControl = await controlFactory.buildControl( @@ -73,10 +64,7 @@ beforeAll(async () => { describe('Incompatible embeddables', () => { test('Action is incompatible with embeddables that are not editable', async () => { - const timeSliderFactory = getTimesliderControlFactory({ - core: mockCore, - data: dataStartServiceMock, - }); + const timeSliderFactory = getTimesliderControlFactory(); const timeSliderUuid = 'timeSliderControl'; const timeSliderControl = await timeSliderFactory.buildControl( {}, diff --git a/src/plugins/controls/public/index.ts b/src/plugins/controls/public/index.ts index 6a490248b8929..6c7a548cb091d 100644 --- a/src/plugins/controls/public/index.ts +++ b/src/plugins/controls/public/index.ts @@ -21,7 +21,6 @@ export { ACTION_CLEAR_CONTROL, ACTION_DELETE_CONTROL, ACTION_EDIT_CONTROL } from export type { DataControlApi, DataControlFactory, - DataControlServices, } from './react_controls/controls/data_controls/types'; export { diff --git a/src/plugins/controls/public/plugin.ts b/src/plugins/controls/public/plugin.ts index 039b960bfc3c5..c6e1a2873b169 100644 --- a/src/plugins/controls/public/plugin.ts +++ b/src/plugins/controls/public/plugin.ts @@ -10,63 +10,36 @@ import type { CoreSetup, CoreStart, Plugin } from '@kbn/core/public'; import { PANEL_HOVER_TRIGGER } from '@kbn/embeddable-plugin/public'; +import { ClearControlAction } from './actions/clear_control_action'; +import { DeleteControlAction } from './actions/delete_control_action'; +import { EditControlAction } from './actions/edit_control_action'; import { registerControlGroupEmbeddable } from './react_controls/control_group/register_control_group_embeddable'; import { registerOptionsListControl } from './react_controls/controls/data_controls/options_list_control/register_options_list_control'; import { registerRangeSliderControl } from './react_controls/controls/data_controls/range_slider/register_range_slider_control'; import { registerTimeSliderControl } from './react_controls/controls/timeslider_control/register_timeslider_control'; -import { controlsService } from './services/controls/controls_service'; -import type { - ControlsPluginSetup, - ControlsPluginSetupDeps, - ControlsPluginStart, - ControlsPluginStartDeps, -} from './types'; +import { setKibanaServices, untilPluginStartServicesReady } from './services/kibana_services'; +import type { ControlsPluginSetupDeps, ControlsPluginStartDeps } from './types'; export class ControlsPlugin - implements - Plugin< - ControlsPluginSetup, - ControlsPluginStart, - ControlsPluginSetupDeps, - ControlsPluginStartDeps - > + implements Plugin { - private async startControlsKibanaServices( - coreStart: CoreStart, - startPlugins: ControlsPluginStartDeps - ) { - const { registry, pluginServices } = await import('./services/plugin_services'); - pluginServices.setRegistry(registry.start({ coreStart, startPlugins })); - } - public setup( - _coreSetup: CoreSetup, + _coreSetup: CoreSetup, _setupPlugins: ControlsPluginSetupDeps - ): ControlsPluginSetup { - const { registerControlFactory } = controlsService; + ) { const { embeddable } = _setupPlugins; - registerControlGroupEmbeddable(_coreSetup, embeddable); - registerOptionsListControl(_coreSetup); - registerRangeSliderControl(_coreSetup); - registerTimeSliderControl(_coreSetup); - - return { - registerControlFactory, - }; + registerControlGroupEmbeddable(embeddable); + registerOptionsListControl(); + registerRangeSliderControl(); + registerTimeSliderControl(); } - public start(coreStart: CoreStart, startPlugins: ControlsPluginStartDeps): ControlsPluginStart { - this.startControlsKibanaServices(coreStart, startPlugins).then(async () => { - const { uiActions } = startPlugins; - - const [{ DeleteControlAction }, { EditControlAction }, { ClearControlAction }] = - await Promise.all([ - import('./actions/delete_control_action'), - import('./actions/edit_control_action'), - import('./actions/clear_control_action'), - ]); + public start(coreStart: CoreStart, startPlugins: ControlsPluginStartDeps) { + const { uiActions } = startPlugins; + setKibanaServices(coreStart, startPlugins); + untilPluginStartServicesReady().then(() => { const deleteControlAction = new DeleteControlAction(); uiActions.registerAction(deleteControlAction); uiActions.attachAction(PANEL_HOVER_TRIGGER, deleteControlAction.id); @@ -79,12 +52,6 @@ export class ControlsPlugin uiActions.registerAction(clearControlAction); uiActions.attachAction(PANEL_HOVER_TRIGGER, clearControlAction.id); }); - - const { getControlFactory, getAllControlTypes } = controlsService; - return { - getControlFactory, - getAllControlTypes, - }; } public stop() {} diff --git a/src/plugins/controls/public/react_controls/control_group/components/control_error.tsx b/src/plugins/controls/public/react_controls/control_group/components/control_error.tsx index 52b9e7d9b806a..2ef6b06faeedd 100644 --- a/src/plugins/controls/public/react_controls/control_group/components/control_error.tsx +++ b/src/plugins/controls/public/react_controls/control_group/components/control_error.tsx @@ -13,8 +13,6 @@ import { EuiButtonEmpty, EuiPopover } from '@elastic/eui'; import { FormattedMessage } from '@kbn/i18n-react'; import { Markdown } from '@kbn/shared-ux-markdown'; -/** TODO: This file is duplicated from the controls plugin to avoid exporting it */ - interface ControlErrorProps { error: Error | string; } diff --git a/src/plugins/controls/public/react_controls/control_group/components/control_group.tsx b/src/plugins/controls/public/react_controls/control_group/components/control_group.tsx index 9c962113d1a7f..54e778684806a 100644 --- a/src/plugins/controls/public/react_controls/control_group/components/control_group.tsx +++ b/src/plugins/controls/public/react_controls/control_group/components/control_group.tsx @@ -30,7 +30,7 @@ import { EuiButtonIcon, EuiFlexGroup, EuiFlexItem, EuiPanel, EuiToolTip } from ' import { css } from '@emotion/react'; import { useBatchedPublishingSubjects } from '@kbn/presentation-publishing'; -import type { ControlStyle } from '../../../../common'; +import type { ControlLabelPosition } from '../../../../common'; import type { DefaultControlApi } from '../../controls/types'; import { ControlGroupStrings } from '../control_group_strings'; import { ControlsInOrder } from '../init_controls_manager'; @@ -49,7 +49,7 @@ interface Props { setControlApi: (uuid: string, controlApi: DefaultControlApi) => void; }; hasUnappliedSelections: boolean; - labelPosition: ControlStyle; + labelPosition: ControlLabelPosition; } export function ControlGroup({ diff --git a/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.test.tsx b/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.test.tsx index 79d0312b29537..b3705106afe2c 100644 --- a/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.test.tsx +++ b/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.test.tsx @@ -15,8 +15,8 @@ import { render } from '@testing-library/react'; import { ControlGroupApi } from '../../..'; import { ControlGroupChainingSystem, - ControlStyle, - DEFAULT_CONTROL_STYLE, + ControlLabelPosition, + DEFAULT_CONTROL_LABEL_POSITION, ParentIgnoreSettings, } from '../../../../common'; import { DefaultControlApi } from '../../controls/types'; @@ -33,7 +33,7 @@ describe('render', () => { onDeleteAll: () => {}, stateManager: { chainingSystem: new BehaviorSubject('HIERARCHICAL'), - labelPosition: new BehaviorSubject(DEFAULT_CONTROL_STYLE), + labelPosition: new BehaviorSubject(DEFAULT_CONTROL_LABEL_POSITION), autoApplySelections: new BehaviorSubject(true), ignoreParentSettings: new BehaviorSubject(undefined), }, diff --git a/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.tsx b/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.tsx index f908a557366fa..c4e7dc61476ba 100644 --- a/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.tsx +++ b/src/plugins/controls/public/react_controls/control_group/components/control_group_editor.tsx @@ -27,7 +27,7 @@ import { } from '@elastic/eui'; import { useBatchedPublishingSubjects } from '@kbn/presentation-publishing'; -import type { ControlStyle, ParentIgnoreSettings } from '../../../../common'; +import type { ControlLabelPosition, ParentIgnoreSettings } from '../../../../common'; import { CONTROL_LAYOUT_OPTIONS } from '../../controls/data_controls/editor_constants'; import type { ControlStateManager } from '../../controls/types'; import { ControlGroupStrings } from '../control_group_strings'; @@ -86,7 +86,7 @@ export const ControlGroupEditor = ({ onCancel, onSave, onDeleteAll, stateManager idSelected={selectedLabelPosition} legend={ControlGroupStrings.management.labelPosition.getLabelPositionLegend()} onChange={(newPosition: string) => { - stateManager.labelPosition.next(newPosition as ControlStyle); + stateManager.labelPosition.next(newPosition as ControlLabelPosition); }} /> diff --git a/src/plugins/controls/public/react_controls/control_group/components/control_panel.test.tsx b/src/plugins/controls/public/react_controls/control_group/components/control_panel.test.tsx index bbf8e8127813e..365c896bb908e 100644 --- a/src/plugins/controls/public/react_controls/control_group/components/control_panel.test.tsx +++ b/src/plugins/controls/public/react_controls/control_group/components/control_panel.test.tsx @@ -14,7 +14,7 @@ import { pluginServices as presentationUtilPluginServices } from '@kbn/presentat import { registry as presentationUtilServicesRegistry } from '@kbn/presentation-util-plugin/public/services/plugin_services.story'; import { render, waitFor } from '@testing-library/react'; -import type { ControlStyle, ControlWidth } from '../../../../common'; +import type { ControlLabelPosition, ControlWidth } from '../../../../common'; import { ControlPanel } from './control_panel'; describe('render', () => { @@ -74,7 +74,7 @@ describe('render', () => { mockApi = { uuid: 'control1', parentApi: { - labelPosition: new BehaviorSubject('oneLine'), + labelPosition: new BehaviorSubject('oneLine'), }, }; const controlPanel = render(); @@ -92,7 +92,7 @@ describe('render', () => { mockApi = { uuid: 'control1', parentApi: { - labelPosition: new BehaviorSubject('twoLine'), + labelPosition: new BehaviorSubject('twoLine'), }, }; const controlPanel = render(); diff --git a/src/plugins/controls/public/react_controls/control_group/get_control_group_factory.tsx b/src/plugins/controls/public/react_controls/control_group/get_control_group_factory.tsx index 6c3e8d10c3c66..77da1480eb494 100644 --- a/src/plugins/controls/public/react_controls/control_group/get_control_group_factory.tsx +++ b/src/plugins/controls/public/react_controls/control_group/get_control_group_factory.tsx @@ -11,9 +11,7 @@ import fastIsEqual from 'fast-deep-equal'; import React, { useEffect } from 'react'; import { BehaviorSubject } from 'rxjs'; -import { CoreStart } from '@kbn/core/public'; import { DataView } from '@kbn/data-views-plugin/common'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; import { ReactEmbeddableFactory } from '@kbn/embeddable-plugin/public'; import { i18n } from '@kbn/i18n'; import { @@ -31,11 +29,11 @@ import type { ControlGroupChainingSystem, ControlGroupRuntimeState, ControlGroupSerializedState, + ControlLabelPosition, ControlPanelsState, - ControlStyle, ParentIgnoreSettings, } from '../../../common'; -import { CONTROL_GROUP_TYPE, DEFAULT_CONTROL_STYLE } from '../../../common'; +import { CONTROL_GROUP_TYPE, DEFAULT_CONTROL_LABEL_POSITION } from '../../../common'; import { openDataControlEditor } from '../controls/data_controls/open_data_control_editor'; import { ControlGroup } from './components/control_group'; import { chaining$, controlFetch$, controlGroupFetch$ } from './control_fetch'; @@ -45,13 +43,11 @@ import { openEditControlGroupFlyout } from './open_edit_control_group_flyout'; import { initSelectionsManager } from './selections_manager'; import type { ControlGroupApi } from './types'; import { deserializeControlGroup } from './utils/serialization_utils'; +import { coreServices, dataViewsService } from '../../services/kibana_services'; const DEFAULT_CHAINING_SYSTEM = 'HIERARCHICAL'; -export const getControlGroupEmbeddableFactory = (services: { - core: CoreStart; - dataViews: DataViewsPublicPluginStart; -}) => { +export const getControlGroupEmbeddableFactory = () => { const controlGroupEmbeddableFactory: ReactEmbeddableFactory< ControlGroupSerializedState, ControlGroupRuntimeState, @@ -75,7 +71,7 @@ export const getControlGroupEmbeddableFactory = (services: { } = initialRuntimeState; const autoApplySelections$ = new BehaviorSubject(autoApplySelections); - const defaultDataViewId = await services.dataViews.getDefaultId(); + const defaultDataViewId = await dataViewsService.getDefaultId(); const lastSavedControlsState$ = new BehaviorSubject( lastSavedRuntimeState.initialChildControlState ); @@ -94,15 +90,12 @@ export const getControlGroupEmbeddableFactory = (services: { const ignoreParentSettings$ = new BehaviorSubject( ignoreParentSettings ); - const labelPosition$ = new BehaviorSubject( // TODO: Rename `ControlStyle` - initialLabelPosition ?? DEFAULT_CONTROL_STYLE // TODO: Rename `DEFAULT_CONTROL_STYLE` + const labelPosition$ = new BehaviorSubject( + initialLabelPosition ?? DEFAULT_CONTROL_LABEL_POSITION ); const allowExpensiveQueries$ = new BehaviorSubject(true); const disabledActionIds$ = new BehaviorSubject(undefined); - /** TODO: Handle loading; loading should be true if any child is loading */ - const dataLoading$ = new BehaviorSubject(false); - const unsavedChanges = initializeControlGroupUnsavedChanges( selectionsManager.applySelections, controlsManager.api.children$, @@ -122,7 +115,10 @@ export const getControlGroupEmbeddableFactory = (services: { (next: ParentIgnoreSettings | undefined) => ignoreParentSettings$.next(next), fastIsEqual, ], - labelPosition: [labelPosition$, (next: ControlStyle) => labelPosition$.next(next)], + labelPosition: [ + labelPosition$, + (next: ControlLabelPosition) => labelPosition$.next(next), + ], }, controlsManager.snapshotControlsRuntimeState, controlsManager.resetControlsUnsavedChanges, @@ -157,18 +153,13 @@ export const getControlGroupEmbeddableFactory = (services: { initialChildControlState: controlsManager.snapshotControlsRuntimeState(), }; }, - dataLoading: dataLoading$, onEdit: async () => { - openEditControlGroupFlyout( - api, - { - chainingSystem: chainingSystem$, - labelPosition: labelPosition$, - autoApplySelections: autoApplySelections$, - ignoreParentSettings: ignoreParentSettings$, - }, - { core: services.core } - ); + openEditControlGroupFlyout(api, { + chainingSystem: chainingSystem$, + labelPosition: labelPosition$, + autoApplySelections: autoApplySelections$, + ignoreParentSettings: ignoreParentSettings$, + }); }, isEditingEnabled: () => true, openAddDataControlFlyout: (settings) => { @@ -193,7 +184,6 @@ export const getControlGroupEmbeddableFactory = (services: { settings?.onSave?.(); }, controlGroupApi: api, - services, }); }, serializeState: () => { @@ -201,7 +191,7 @@ export const getControlGroupEmbeddableFactory = (services: { return { rawState: { chainingSystem: chainingSystem$.getValue(), - controlStyle: labelPosition$.getValue(), // Rename "labelPosition" to "controlStyle" + controlStyle: labelPosition$.getValue(), showApplySelections: !autoApplySelections$.getValue(), ignoreParentSettingsJSON: JSON.stringify(ignoreParentSettings$.getValue()), panelsJSON, @@ -265,10 +255,9 @@ export const getControlGroupEmbeddableFactory = (services: { /** Fetch the allowExpensiveQuries setting for the children to use if necessary */ const fetchAllowExpensiveQueries = async () => { try { - const { allowExpensiveQueries } = await services.core.http.get<{ + const { allowExpensiveQueries } = await coreServices.http.get<{ allowExpensiveQueries: boolean; - // TODO: Rename this route as part of https://github.com/elastic/kibana/issues/174961 - }>('/internal/controls/optionsList/getExpensiveQueriesSetting', { + }>('/internal/controls/getExpensiveQueriesSetting', { version: '1', }); if (!allowExpensiveQueries) { diff --git a/src/plugins/controls/public/react_controls/control_group/open_edit_control_group_flyout.tsx b/src/plugins/controls/public/react_controls/control_group/open_edit_control_group_flyout.tsx index 5e7026282123a..5e7baf1f73e5d 100644 --- a/src/plugins/controls/public/react_controls/control_group/open_edit_control_group_flyout.tsx +++ b/src/plugins/controls/public/react_controls/control_group/open_edit_control_group_flyout.tsx @@ -8,7 +8,6 @@ */ import { OverlayRef } from '@kbn/core-mount-utils-browser'; -import { CoreStart } from '@kbn/core/public'; import { i18n } from '@kbn/i18n'; import { tracksOverlays } from '@kbn/presentation-containers'; import { apiHasParentApi } from '@kbn/presentation-publishing'; @@ -19,13 +18,11 @@ import { BehaviorSubject } from 'rxjs'; import { ControlStateManager } from '../controls/types'; import { ControlGroupEditor } from './components/control_group_editor'; import { ControlGroupApi, ControlGroupEditorState } from './types'; +import { coreServices } from '../../services/kibana_services'; export const openEditControlGroupFlyout = ( controlGroupApi: ControlGroupApi, - stateManager: ControlStateManager, - services: { - core: CoreStart; - } + stateManager: ControlStateManager ) => { /** * Duplicate all state into a new manager because we do not want to actually apply the changes @@ -50,7 +47,7 @@ export const openEditControlGroupFlyout = ( }; const onDeleteAll = (ref: OverlayRef) => { - services.core.overlays + coreServices.overlays .openConfirm( i18n.translate('controls.controlGroup.management.delete.sub', { defaultMessage: 'Controls are not recoverable once removed.', @@ -77,7 +74,7 @@ export const openEditControlGroupFlyout = ( }); }; - const overlay = services.core.overlays.openFlyout( + const overlay = coreServices.overlays.openFlyout( toMountPoint( closeOverlay(overlay)} />, { - theme: services.core.theme, - i18n: services.core.i18n, + theme: coreServices.theme, + i18n: coreServices.i18n, } ), { diff --git a/src/plugins/controls/public/react_controls/control_group/register_control_group_embeddable.ts b/src/plugins/controls/public/react_controls/control_group/register_control_group_embeddable.ts index 513633e46a875..a64faa63e8efc 100644 --- a/src/plugins/controls/public/react_controls/control_group/register_control_group_embeddable.ts +++ b/src/plugins/controls/public/react_controls/control_group/register_control_group_embeddable.ts @@ -7,23 +7,16 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import type { CoreSetup } from '@kbn/core/public'; import type { EmbeddableSetup } from '@kbn/embeddable-plugin/public'; -import type { ControlsPluginStartDeps } from '../../types'; import { CONTROL_GROUP_TYPE } from '../../../common'; +import { untilPluginStartServicesReady } from '../../services/kibana_services'; -export function registerControlGroupEmbeddable( - coreSetup: CoreSetup, - embeddableSetup: EmbeddableSetup -) { +export function registerControlGroupEmbeddable(embeddableSetup: EmbeddableSetup) { embeddableSetup.registerReactEmbeddableFactory(CONTROL_GROUP_TYPE, async () => { - const [{ getControlGroupEmbeddableFactory }, [coreStart, depsStart]] = await Promise.all([ + const [{ getControlGroupEmbeddableFactory }] = await Promise.all([ import('./get_control_group_factory'), - coreSetup.getStartServices(), + untilPluginStartServicesReady(), ]); - return getControlGroupEmbeddableFactory({ - core: coreStart, - dataViews: depsStart.data.dataViews, - }); + return getControlGroupEmbeddableFactory(); }); } diff --git a/src/plugins/controls/public/react_controls/control_group/types.ts b/src/plugins/controls/public/react_controls/control_group/types.ts index cb09cac975e7a..37f9f40c4079f 100644 --- a/src/plugins/controls/public/react_controls/control_group/types.ts +++ b/src/plugins/controls/public/react_controls/control_group/types.ts @@ -19,7 +19,6 @@ import { import { HasEditCapabilities, HasParentApi, - PublishesDataLoading, PublishesDisabledActionIds, PublishesFilters, PublishesTimeslice, @@ -35,8 +34,8 @@ import { ControlGroupEditorConfig, ControlGroupRuntimeState, ControlGroupSerializedState, + ControlLabelPosition, ControlPanelState, - ControlStyle, DefaultControlState, ParentIgnoreSettings, } from '../../../common'; @@ -54,7 +53,6 @@ export type ControlGroupApi = PresentationContainer & PublishesDataViews & HasSerializedChildState & HasEditCapabilities & - PublishesDataLoading & Pick, 'unsavedChanges'> & PublishesTimeslice & PublishesDisabledActionIds & @@ -62,7 +60,7 @@ export type ControlGroupApi = PresentationContainer & allowExpensiveQueries$: PublishingSubject; autoApplySelections$: PublishingSubject; ignoreParentSettings$: PublishingSubject; - labelPosition: PublishingSubject; + labelPosition: PublishingSubject; asyncResetUnsavedChanges: () => Promise; controlFetch$: (controlUuid: string) => Observable; diff --git a/src/plugins/controls/public/react_controls/control_group/utils/control_group_state_builder.ts b/src/plugins/controls/public/react_controls/control_group/utils/control_group_state_builder.ts index 91e5379416c5e..1c051e58af46f 100644 --- a/src/plugins/controls/public/react_controls/control_group/utils/control_group_state_builder.ts +++ b/src/plugins/controls/public/react_controls/control_group/utils/control_group_state_builder.ts @@ -13,11 +13,12 @@ import { OPTIONS_LIST_CONTROL, RANGE_SLIDER_CONTROL, TIME_SLIDER_CONTROL, + type ControlGroupRuntimeState, + type ControlPanelsState, type DefaultDataControlState, } from '../../../../common'; -import { type ControlGroupRuntimeState, type ControlPanelsState } from '../../../../common'; import type { OptionsListControlState } from '../../../../common/options_list'; -import { pluginServices } from '../../../services'; +import { dataViewsService } from '../../../services/kibana_services'; import { getDataControlFieldRegistry } from '../../controls/data_controls/data_control_editor_utils'; import type { RangesliderControlState } from '../../controls/data_controls/range_slider/types'; @@ -82,7 +83,7 @@ export const controlGroupStateBuilder = { }; async function getCompatibleControlType(dataViewId: string, fieldName: string) { - const dataView = await pluginServices.getServices().dataViews.get(dataViewId); + const dataView = await dataViewsService.get(dataViewId); const fieldRegistry = await getDataControlFieldRegistry(dataView); const field = fieldRegistry[fieldName]; if (field.compatibleControlTypes.length === 0) { diff --git a/src/plugins/controls/public/react_controls/control_group/utils/initialization_utils.ts b/src/plugins/controls/public/react_controls/control_group/utils/initialization_utils.ts index 8bd19c3d6478c..ef81b4e30b361 100644 --- a/src/plugins/controls/public/react_controls/control_group/utils/initialization_utils.ts +++ b/src/plugins/controls/public/react_controls/control_group/utils/initialization_utils.ts @@ -7,11 +7,11 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { type ControlGroupRuntimeState, DEFAULT_CONTROL_STYLE } from '../../../../common'; +import { DEFAULT_CONTROL_LABEL_POSITION, type ControlGroupRuntimeState } from '../../../../common'; export const getDefaultControlGroupRuntimeState = (): ControlGroupRuntimeState => ({ initialChildControlState: {}, - labelPosition: DEFAULT_CONTROL_STYLE, + labelPosition: DEFAULT_CONTROL_LABEL_POSITION, chainingSystem: 'HIERARCHICAL', autoApplySelections: true, ignoreParentSettings: { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.test.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.test.tsx index 5f8f17c57bce5..8d8385d603fb3 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.test.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.test.tsx @@ -12,7 +12,6 @@ import { BehaviorSubject } from 'rxjs'; import { createStubDataView } from '@kbn/data-views-plugin/common/data_view.stub'; import { stubFieldSpecMap } from '@kbn/data-views-plugin/common/field.stub'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { TimeRange } from '@kbn/es-query'; import { I18nProvider } from '@kbn/i18n-react'; import { act, fireEvent, render, RenderResult, waitFor } from '@testing-library/react'; @@ -22,6 +21,7 @@ import { DEFAULT_CONTROL_WIDTH, type DefaultDataControlState, } from '../../../../common'; +import { dataViewsService } from '../../../services/kibana_services'; import { getAllControlTypes, getControlFactory } from '../../control_factory_registry'; import type { ControlGroupApi } from '../../control_group/types'; import type { ControlFactory } from '../types'; @@ -39,7 +39,6 @@ jest.mock('../../control_factory_registry', () => ({ getControlFactory: jest.fn(), })); -const mockDataViews = dataViewPluginMocks.createStartContract(); const mockDataView = createStubDataView({ spec: { id: 'logstash-*', @@ -58,7 +57,6 @@ const mockDataView = createStubDataView({ timeFieldName: '@timestamp', }, }); -mockDataViews.get = jest.fn().mockResolvedValue(mockDataView); const dashboardApi = { timeRange$: new BehaviorSubject(undefined), @@ -82,7 +80,7 @@ describe('Data control editor', () => { controlType?: string; initialDefaultPanelTitle?: string; }) => { - mockDataViews.get = jest.fn().mockResolvedValue(mockDataView); + dataViewsService.get = jest.fn().mockResolvedValue(mockDataView); const controlEditor = render( @@ -97,13 +95,12 @@ describe('Data control editor', () => { controlId={controlId} controlType={controlType} initialDefaultPanelTitle={initialDefaultPanelTitle} - services={{ dataViews: mockDataViews }} /> ); await waitFor(() => { - expect(mockDataViews.get).toHaveBeenCalledTimes(1); + expect(dataViewsService.get).toHaveBeenCalledTimes(1); }); return controlEditor; diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.tsx index 5254fe200e97c..35e21ca3b407a 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/data_control_editor.tsx @@ -33,7 +33,6 @@ import { EuiToolTip, } from '@elastic/eui'; import { DataViewField } from '@kbn/data-views-plugin/common'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; import { LazyDataViewPicker, LazyFieldPicker, @@ -46,6 +45,7 @@ import { type ControlWidth, type DefaultDataControlState, } from '../../../../common'; +import { dataViewsService } from '../../../services/kibana_services'; import { getAllControlTypes, getControlFactory } from '../../control_factory_registry'; import type { ControlGroupApi } from '../../control_group/types'; import { DataControlEditorStrings } from './data_control_constants'; @@ -67,9 +67,6 @@ export interface ControlEditorProps< controlGroupApi: ControlGroupApi; // controls must always have a parent API onCancel: (newState: Partial) => void; onSave: (newState: Partial, type: string) => void; - services: { - dataViews: DataViewsPublicPluginStart; - }; } const FieldPicker = withSuspense(LazyFieldPicker, null); @@ -151,8 +148,6 @@ export const DataControlEditor = ) => { const [editorState, setEditorState] = useState>(initialState); const [defaultPanelTitle, setDefaultPanelTitle] = useState( @@ -163,16 +158,14 @@ export const DataControlEditor = (true); const editorConfig = useMemo(() => controlGroupApi.getEditorConfig(), [controlGroupApi]); - // TODO: Maybe remove `useAsync` - see https://github.com/elastic/kibana/pull/182842#discussion_r1624909709 const { loading: dataViewListLoading, value: dataViewListItems = [], error: dataViewListError, } = useAsync(async () => { - return dataViewService.getIdsWithTitle(); + return dataViewsService.getIdsWithTitle(); }); - // TODO: Maybe remove `useAsync` - see https://github.com/elastic/kibana/pull/182842#discussion_r1624909709 const { loading: dataViewLoading, value: { selectedDataView, fieldRegistry } = { @@ -185,7 +178,7 @@ export const DataControlEditor = { return await loadFieldRegistryFromDataView(dataView); @@ -21,7 +20,6 @@ export const getDataControlFieldRegistry = memoize( (dataView: DataView) => [dataView.id, JSON.stringify(dataView.fields.getAll())].join('|') ); -/** TODO: This function is duplicated from the controls plugin to avoid exporting it */ const loadFieldRegistryFromDataView = async ( dataView: DataView ): Promise => { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.test.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.test.tsx index 8ff50a2bc4ada..d189d0aaa1ae9 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.test.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.test.tsx @@ -7,10 +7,9 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { coreMock } from '@kbn/core/public/mocks'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import type { DataView } from '@kbn/data-views-plugin/public'; import { first, skip } from 'rxjs'; +import { dataViewsService } from '../../../services/kibana_services'; import { ControlGroupApi } from '../../control_group/types'; import { initializeDataControl } from './initialize_data_control'; @@ -21,9 +20,8 @@ describe('initializeDataControl', () => { }; const editorStateManager = {}; const controlGroupApi = {} as unknown as ControlGroupApi; - const mockDataViews = dataViewPluginMocks.createStartContract(); - // @ts-ignore - mockDataViews.get = async (id: string): Promise => { + + dataViewsService.get = async (id: string): Promise => { if (id !== 'myDataViewId') { throw new Error(`Simulated error: no data view found for id ${id}`); } @@ -40,10 +38,6 @@ describe('initializeDataControl', () => { }, } as unknown as DataView; }; - const services = { - core: coreMock.createStart(), - dataViews: mockDataViews, - }; describe('dataViewId subscription', () => { describe('no blocking errors', () => { @@ -55,8 +49,7 @@ describe('initializeDataControl', () => { 'referenceNameSuffix', dataControlState, editorStateManager, - controlGroupApi, - services + controlGroupApi ); dataControl.api.defaultPanelTitle!.pipe(skip(1), first()).subscribe(() => { @@ -90,8 +83,7 @@ describe('initializeDataControl', () => { dataViewId: 'notGonnaFindMeDataViewId', }, editorStateManager, - controlGroupApi, - services + controlGroupApi ); dataControl.api.dataViews.pipe(skip(1), first()).subscribe(() => { @@ -129,8 +121,7 @@ describe('initializeDataControl', () => { fieldName: 'notGonnaFindMeFieldName', }, editorStateManager, - controlGroupApi, - services + controlGroupApi ); dataControl.api.defaultPanelTitle!.pipe(skip(1), first()).subscribe(() => { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.ts b/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.ts index 6b814efa1ec3d..11fb453d56350 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/initialize_data_control.ts @@ -10,19 +10,18 @@ import { isEqual } from 'lodash'; import { BehaviorSubject, combineLatest, debounceTime, first, skip, switchMap, tap } from 'rxjs'; -import { CoreStart } from '@kbn/core-lifecycle-browser'; import { DATA_VIEW_SAVED_OBJECT_TYPE, DataView, DataViewField, } from '@kbn/data-views-plugin/common'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; import { Filter } from '@kbn/es-query'; import { SerializedPanelState } from '@kbn/presentation-containers'; import { StateComparators } from '@kbn/presentation-publishing'; import { i18n } from '@kbn/i18n'; import type { DefaultControlState, DefaultDataControlState } from '../../../../common'; +import { dataViewsService } from '../../../services/kibana_services'; import type { ControlGroupApi } from '../../control_group/types'; import { initializeDefaultControlApi } from '../initialize_default_control_api'; import type { ControlApiInitialization, ControlStateManager } from '../types'; @@ -40,11 +39,7 @@ export const initializeDataControl = ( * responsible for managing */ editorStateManager: ControlStateManager, - controlGroupApi: ControlGroupApi, - services: { - core: CoreStart; - dataViews: DataViewsPublicPluginStart; - } + controlGroupApi: ControlGroupApi ): { api: ControlApiInitialization; cleanup: () => void; @@ -88,7 +83,7 @@ export const initializeDataControl = ( switchMap(async (currentDataViewId) => { let dataView: DataView | undefined; try { - dataView = await services.dataViews.get(currentDataViewId); + dataView = await dataViewsService.get(currentDataViewId); return { dataView }; } catch (error) { return { error }; @@ -156,7 +151,6 @@ export const initializeDataControl = ( // open the editor to get the new state openDataControlEditor({ - services, onSave: ({ type: newType, state: newState }) => { if (newType === controlType) { // apply the changes from the new state via the state manager diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/open_data_control_editor.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/open_data_control_editor.tsx index fe629555dea3c..08118702a003e 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/open_data_control_editor.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/open_data_control_editor.tsx @@ -10,14 +10,14 @@ import React from 'react'; import deepEqual from 'react-fast-compare'; -import { CoreStart, OverlayRef } from '@kbn/core/public'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; +import { OverlayRef } from '@kbn/core/public'; import { i18n } from '@kbn/i18n'; import { tracksOverlays } from '@kbn/presentation-containers'; import { apiHasParentApi } from '@kbn/presentation-publishing'; import { toMountPoint } from '@kbn/react-kibana-mount'; import type { DefaultDataControlState } from '../../../../common'; +import { coreServices } from '../../../services/kibana_services'; import type { ControlGroupApi } from '../../control_group/types'; import { DataControlEditor } from './data_control_editor'; @@ -30,7 +30,6 @@ export const openDataControlEditor = < initialDefaultPanelTitle, onSave, controlGroupApi, - services, }: { initialState: Partial; controlType?: string; @@ -38,10 +37,6 @@ export const openDataControlEditor = < initialDefaultPanelTitle?: string; onSave: ({ type, state }: { type: string; state: Partial }) => void; controlGroupApi: ControlGroupApi; - services: { - core: CoreStart; - dataViews: DataViewsPublicPluginStart; - }; }): void => { const closeOverlay = (overlayRef: OverlayRef) => { if (apiHasParentApi(controlGroupApi) && tracksOverlays(controlGroupApi.parentApi)) { @@ -55,7 +50,7 @@ export const openDataControlEditor = < closeOverlay(overlay); return; } - services.core.overlays + coreServices.overlays .openConfirm( i18n.translate('controls.controlGroup.management.discard.sub', { defaultMessage: `Changes that you've made to this control will be discarded, are you sure you want to continue?`, @@ -80,7 +75,7 @@ export const openDataControlEditor = < }); }; - const overlay = services.core.overlays.openFlyout( + const overlay = coreServices.overlays.openFlyout( toMountPoint( controlGroupApi={controlGroupApi} @@ -95,11 +90,10 @@ export const openDataControlEditor = < closeOverlay(overlay); onSave({ type: selectedControlType, state }); }} - services={{ dataViews: services.dataViews }} />, { - theme: services.core.theme, - i18n: services.core.i18n, + theme: coreServices.theme, + i18n: coreServices.i18n, } ), { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/fetch_and_validate.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/fetch_and_validate.tsx index c2b1d7d84250e..2e2cd341e8704 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/fetch_and_validate.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/fetch_and_validate.tsx @@ -26,13 +26,11 @@ import { isValidSearch } from '../../../../../common/options_list/is_valid_searc import { OptionsListSelection } from '../../../../../common/options_list/options_list_selections'; import { ControlFetchContext } from '../../../control_group/control_fetch'; import { ControlStateManager } from '../../types'; -import { DataControlServices } from '../types'; import { OptionsListFetchCache } from './options_list_fetch_cache'; import { OptionsListComponentApi, OptionsListComponentState, OptionsListControlApi } from './types'; export function fetchAndValidate$({ api, - services, stateManager, }: { api: Pick & @@ -41,7 +39,6 @@ export function fetchAndValidate$({ loadingSuggestions$: BehaviorSubject; debouncedSearchString: Observable; }; - services: DataControlServices; stateManager: ControlStateManager< Pick > & { @@ -126,7 +123,7 @@ export function fetchAndValidate$({ const newAbortController = new AbortController(); abortController = newAbortController; try { - return await requestCache.runFetchRequest(request, newAbortController.signal, services); + return await requestCache.runFetchRequest(request, newAbortController.signal); } catch (error) { return { error }; } diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.test.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.test.tsx index 99e15a3d0f31f..20911d1cdb872 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.test.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.test.tsx @@ -9,26 +9,22 @@ import React from 'react'; -import { coreMock } from '@kbn/core/public/mocks'; -import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; import { DataView } from '@kbn/data-views-plugin/common'; import { createStubDataView } from '@kbn/data-views-plugin/common/data_view.stub'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { act, render, waitFor } from '@testing-library/react'; import userEvent from '@testing-library/user-event'; +import { coreServices, dataViewsService } from '../../../../services/kibana_services'; import { getMockedBuildApi, getMockedControlGroupApi } from '../../mocks/control_mocks'; import { getOptionsListControlFactory } from './get_options_list_control_factory'; describe('Options List Control Api', () => { const uuid = 'myControl1'; const controlGroupApi = getMockedControlGroupApi(); - const mockDataViews = dataViewPluginMocks.createStartContract(); - const mockCore = coreMock.createStart(); const waitOneTick = () => act(() => new Promise((resolve) => setTimeout(resolve, 0))); - mockDataViews.get = jest.fn().mockImplementation(async (id: string): Promise => { + dataViewsService.get = jest.fn().mockImplementation(async (id: string): Promise => { if (id !== 'myDataViewId') { throw new Error(`Simulated error: no data view found for id ${id}`); } @@ -60,11 +56,7 @@ describe('Options List Control Api', () => { return stubDataView; }); - const factory = getOptionsListControlFactory({ - core: mockCore, - data: dataPluginMock.createStartContract(), - dataViews: mockDataViews, - }); + const factory = getOptionsListControlFactory(); describe('filters$', () => { test('should not set filters$ when selectedOptions is not provided', async () => { @@ -177,7 +169,7 @@ describe('Options List Control Api', () => { describe('make selection', () => { beforeAll(() => { - mockCore.http.fetch = jest.fn().mockResolvedValue({ + coreServices.http.fetch = jest.fn().mockResolvedValue({ suggestions: [ { value: 'woof', docCount: 10 }, { value: 'bark', docCount: 15 }, diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.tsx index d0c40736552ce..2a23ac9341ab9 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/get_options_list_control_factory.tsx @@ -9,7 +9,7 @@ import fastIsEqual from 'fast-deep-equal'; import React, { useEffect } from 'react'; -import { BehaviorSubject, combineLatest, debounceTime, filter, skip } from 'rxjs'; +import { BehaviorSubject, combineLatest, debounceTime, filter, map, skip } from 'rxjs'; import { buildExistsFilter, buildPhraseFilter, buildPhrasesFilter, Filter } from '@kbn/es-query'; import { useBatchedPublishingSubjects } from '@kbn/presentation-publishing'; @@ -25,7 +25,7 @@ import type { } from '../../../../../common/options_list'; import { getSelectionAsFieldType, isValidSearch } from '../../../../../common/options_list'; import { initializeDataControl } from '../initialize_data_control'; -import type { DataControlFactory, DataControlServices } from '../types'; +import type { DataControlFactory } from '../types'; import { OptionsListControl } from './components/options_list_control'; import { OptionsListEditorOptions } from './components/options_list_editor_options'; import { @@ -39,9 +39,10 @@ import { initializeOptionsListSelections } from './options_list_control_selectio import { OptionsListStrings } from './options_list_strings'; import type { OptionsListControlApi } from './types'; -export const getOptionsListControlFactory = ( - services: DataControlServices -): DataControlFactory => { +export const getOptionsListControlFactory = (): DataControlFactory< + OptionsListControlState, + OptionsListControlApi +> => { return { type: OPTIONS_LIST_CONTROL, order: 3, // should always be first, since this is the most popular control @@ -78,6 +79,7 @@ export const getOptionsListControlFactory = ( const searchStringValid$ = new BehaviorSubject(true); const requestSize$ = new BehaviorSubject(MIN_OPTIONS_LIST_REQUEST_SIZE); + const dataLoading$ = new BehaviorSubject(undefined); const availableOptions$ = new BehaviorSubject(undefined); const invalidSelections$ = new BehaviorSubject>(new Set()); const totalCardinality$ = new BehaviorSubject(0); @@ -90,8 +92,7 @@ export const getOptionsListControlFactory = ( 'optionsListDataView', initialState, { searchTechnique: searchTechnique$, singleSelect: singleSelect$ }, - controlGroupApi, - services + controlGroupApi ); const selections = initializeOptionsListSelections( @@ -115,12 +116,16 @@ export const getOptionsListControlFactory = ( /** Handle loading state; since suggestion fetching and validation are tied, only need one loading subject */ const loadingSuggestions$ = new BehaviorSubject(false); - const dataLoadingSubscription = loadingSuggestions$ + const dataLoadingSubscription = combineLatest([ + loadingSuggestions$, + dataControl.api.dataLoading, + ]) .pipe( - debounceTime(100) // debounce set loading so that it doesn't flash as the user types + debounceTime(100), // debounce set loading so that it doesn't flash as the user types + map((values) => values.some((value) => value)) ) .subscribe((isLoading) => { - dataControl.api.setDataLoading(isLoading); + dataLoading$.next(isLoading); }); /** Debounce the search string changes to reduce the number of fetch requests */ @@ -161,7 +166,6 @@ export const getOptionsListControlFactory = ( /** Fetch the suggestions and perform validation */ const loadMoreSubject = new BehaviorSubject(null); const fetchSubscription = fetchAndValidate$({ - services, api: { ...dataControl.api, loadMoreSubject, @@ -235,6 +239,7 @@ export const getOptionsListControlFactory = ( const api = buildApi( { ...dataControl.api, + dataLoading: dataLoading$, getTypeDisplayName: OptionsListStrings.control.getDisplayName, serializeState: () => { const { rawState: dataControlState, references } = dataControl.serialize(); diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/options_list_fetch_cache.ts b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/options_list_fetch_cache.ts index 548b1efebd02a..60b1463118733 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/options_list_fetch_cache.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/options_list_fetch_cache.ts @@ -20,7 +20,7 @@ import type { OptionsListResponse, OptionsListSuccessResponse, } from '../../../../../common/options_list/types'; -import type { DataControlServices } from '../types'; +import { coreServices, dataService } from '../../../../services/kibana_services'; const REQUEST_CACHE_SIZE = 50; // only store a max of 50 responses const REQUEST_CACHE_TTL = 1000 * 60; // time to live = 1 minute @@ -80,8 +80,7 @@ export class OptionsListFetchCache { public async runFetchRequest( request: OptionsListRequest, - abortSignal: AbortSignal, - services: DataControlServices + abortSignal: AbortSignal ): Promise { const requestHash = this.getRequestHash(request); @@ -90,11 +89,11 @@ export class OptionsListFetchCache { } else { const index = request.dataView.getIndexPattern(); - const timeService = services.data.query.timefilter.timefilter; + const timeService = dataService.query.timefilter.timefilter; const { query, filters, dataView, timeRange, field, ...passThroughProps } = request; const timeFilter = timeRange ? timeService.createFilter(dataView, timeRange) : undefined; const filtersToUse = [...(filters ?? []), ...(timeFilter ? [timeFilter] : [])]; - const config = getEsQueryConfig(services.core.uiSettings); + const config = getEsQueryConfig(coreServices.uiSettings); const esFilters = [buildEsQuery(dataView, query ?? [], filtersToUse ?? [], config)]; const requestBody = { @@ -105,7 +104,7 @@ export class OptionsListFetchCache { runtimeFieldMap: dataView.toSpec?.().runtimeFieldMap, }; - const result = await services.core.http.fetch( + const result = await coreServices.http.fetch( `/internal/controls/optionsList/${index}`, { version: '1', diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/register_options_list_control.ts b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/register_options_list_control.ts index 417eb42d4b1bd..b58189a75daca 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/register_options_list_control.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/options_list_control/register_options_list_control.ts @@ -7,21 +7,16 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import type { CoreSetup } from '@kbn/core/public'; -import type { ControlsPluginStartDeps } from '../../../../types'; -import { registerControlFactory } from '../../../control_factory_registry'; import { OPTIONS_LIST_CONTROL } from '../../../../../common'; +import { untilPluginStartServicesReady } from '../../../../services/kibana_services'; +import { registerControlFactory } from '../../../control_factory_registry'; -export function registerOptionsListControl(coreSetup: CoreSetup) { +export function registerOptionsListControl() { registerControlFactory(OPTIONS_LIST_CONTROL, async () => { - const [{ getOptionsListControlFactory }, [coreStart, depsStart]] = await Promise.all([ + const [{ getOptionsListControlFactory }] = await Promise.all([ import('./get_options_list_control_factory'), - coreSetup.getStartServices(), + untilPluginStartServicesReady(), ]); - return getOptionsListControlFactory({ - core: coreStart, - data: depsStart.data, - dataViews: depsStart.data.dataViews, - }); + return getOptionsListControlFactory(); }); } diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.test.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.test.tsx index 76cb52981e8c1..925ec3443849a 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.test.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.test.tsx @@ -11,13 +11,11 @@ import React from 'react'; import { of } from 'rxjs'; import { estypes } from '@elastic/elasticsearch'; -import { coreMock } from '@kbn/core/public/mocks'; -import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; import { DataViewField } from '@kbn/data-views-plugin/common'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { SerializedPanelState } from '@kbn/presentation-containers'; import { fireEvent, render, waitFor } from '@testing-library/react'; +import { dataService, dataViewsService } from '../../../../services/kibana_services'; import { getMockedBuildApi, getMockedControlGroupApi } from '../../mocks/control_mocks'; import { getRangesliderControlFactory } from './get_range_slider_control_factory'; import { RangesliderControlState } from './types'; @@ -31,11 +29,10 @@ describe('RangesliderControlApi', () => { const controlGroupApi = getMockedControlGroupApi(); - const dataStartServiceMock = dataPluginMock.createStartContract(); let totalResults = DEFAULT_TOTAL_RESULTS; let min: estypes.AggregationsSingleMetricAggregateBase['value'] = DEFAULT_MIN; let max: estypes.AggregationsSingleMetricAggregateBase['value'] = DEFAULT_MAX; - dataStartServiceMock.search.searchSource.create = jest.fn().mockImplementation(() => { + dataService.search.searchSource.create = jest.fn().mockImplementation(() => { let isAggsRequest = false; return { setField: (key: string) => { @@ -54,9 +51,8 @@ describe('RangesliderControlApi', () => { }, }; }); - const mockDataViews = dataViewPluginMocks.createStartContract(); - mockDataViews.get = jest.fn().mockImplementation(async (id: string): Promise => { + dataViewsService.get = jest.fn().mockImplementation(async (id: string): Promise => { if (id !== 'myDataViewId') { throw new Error(`no data view found for id ${id}`); } @@ -82,11 +78,7 @@ describe('RangesliderControlApi', () => { } as unknown as DataView; }); - const factory = getRangesliderControlFactory({ - core: coreMock.createStart(), - data: dataStartServiceMock, - dataViews: mockDataViews, - }); + const factory = getRangesliderControlFactory(); beforeEach(() => { totalResults = DEFAULT_TOTAL_RESULTS; diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.tsx b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.tsx index 596206dc2f4f6..3ad3b97af7414 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.tsx +++ b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/get_range_slider_control_factory.tsx @@ -16,7 +16,7 @@ import { useBatchedPublishingSubjects } from '@kbn/presentation-publishing'; import { RANGE_SLIDER_CONTROL } from '../../../../../common'; import { initializeDataControl } from '../initialize_data_control'; -import type { DataControlFactory, DataControlServices } from '../types'; +import type { DataControlFactory } from '../types'; import { RangeSliderControl } from './components/range_slider_control'; import { hasNoResults$ } from './has_no_results'; import { minMax$ } from './min_max'; @@ -24,9 +24,10 @@ import { initializeRangeControlSelections } from './range_control_selections'; import { RangeSliderStrings } from './range_slider_strings'; import type { RangesliderControlApi, RangesliderControlState } from './types'; -export const getRangesliderControlFactory = ( - services: DataControlServices -): DataControlFactory => { +export const getRangesliderControlFactory = (): DataControlFactory< + RangesliderControlState, + RangesliderControlApi +> => { return { type: RANGE_SLIDER_CONTROL, getIconType: () => 'controlsHorizontal', @@ -71,8 +72,7 @@ export const getRangesliderControlFactory = ( { step: step$, }, - controlGroupApi, - services + controlGroupApi ); const selections = initializeRangeControlSelections( @@ -111,13 +111,14 @@ export const getRangesliderControlFactory = ( } ); - const dataLoadingSubscription = combineLatest([loadingMinMax$, loadingHasNoResults$]) + const dataLoadingSubscription = combineLatest([ + loadingMinMax$, + loadingHasNoResults$, + dataControl.api.dataLoading, + ]) .pipe( - map((values) => { - return values.some((value) => { - return value; - }); - }) + debounceTime(100), + map((values) => values.some((value) => value)) ) .subscribe((isLoading) => { dataLoading$.next(isLoading); @@ -138,7 +139,6 @@ export const getRangesliderControlFactory = ( const min$ = new BehaviorSubject(undefined); const minMaxSubscription = minMax$({ controlFetch$, - data: services.data, dataViews$: dataControl.api.dataViews, fieldName$: dataControl.stateManager.fieldName, setIsLoading: (isLoading: boolean) => { @@ -198,7 +198,6 @@ export const getRangesliderControlFactory = ( const selectionHasNoResults$ = new BehaviorSubject(false); const hasNotResultsSubscription = hasNoResults$({ controlFetch$, - data: services.data, dataViews$: dataControl.api.dataViews, rangeFilters$: dataControl.api.filters$, ignoreParentSettings$: controlGroupApi.ignoreParentSettings$, diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/has_no_results.ts b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/has_no_results.ts index 27676f5f7b649..24d4510b3fc22 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/has_no_results.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/has_no_results.ts @@ -8,25 +8,23 @@ */ import { estypes } from '@elastic/elasticsearch'; -import { DataPublicPluginStart } from '@kbn/data-plugin/public'; import { DataView } from '@kbn/data-views-plugin/public'; import { AggregateQuery, Filter, Query, TimeRange } from '@kbn/es-query'; import { PublishesDataViews } from '@kbn/presentation-publishing'; -import { combineLatest, lastValueFrom, Observable, switchMap, tap } from 'rxjs'; +import { Observable, combineLatest, lastValueFrom, switchMap, tap } from 'rxjs'; +import { dataService } from '../../../../services/kibana_services'; import { ControlFetchContext } from '../../../control_group/control_fetch'; import { ControlGroupApi } from '../../../control_group/types'; import { DataControlApi } from '../types'; export function hasNoResults$({ controlFetch$, - data, dataViews$, rangeFilters$, ignoreParentSettings$, setIsLoading, }: { controlFetch$: Observable; - data: DataPublicPluginStart; dataViews$?: PublishesDataViews['dataViews']; rangeFilters$: DataControlApi['filters$']; ignoreParentSettings$: ControlGroupApi['ignoreParentSettings$']; @@ -53,7 +51,6 @@ export function hasNoResults$({ prevRequestAbortController = abortController; return await hasNoResults({ abortSignal: abortController.signal, - data, dataView, rangeFilter, ...controlFetchContext, @@ -71,7 +68,6 @@ export function hasNoResults$({ async function hasNoResults({ abortSignal, - data, dataView, filters, query, @@ -79,14 +75,13 @@ async function hasNoResults({ timeRange, }: { abortSignal: AbortSignal; - data: DataPublicPluginStart; dataView: DataView; filters?: Filter[]; query?: Query | AggregateQuery; rangeFilter: Filter; timeRange?: TimeRange; }): Promise { - const searchSource = await data.search.searchSource.create(); + const searchSource = await dataService.search.searchSource.create(); searchSource.setField('size', 0); searchSource.setField('index', dataView); // Tracking total hits accurately has a performance cost @@ -97,7 +92,7 @@ async function hasNoResults({ const allFilters = filters ? [...filters] : []; allFilters.push(rangeFilter); if (timeRange) { - const timeFilter = data.query.timefilter.timefilter.createFilter(dataView, timeRange); + const timeFilter = dataService.query.timefilter.timefilter.createFilter(dataView, timeRange); if (timeFilter) allFilters.push(timeFilter); } if (allFilters.length) { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/min_max.ts b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/min_max.ts index d3335e182f101..8e4d5e00374af 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/min_max.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/min_max.ts @@ -8,26 +8,24 @@ */ import { estypes } from '@elastic/elasticsearch'; -import { DataPublicPluginStart } from '@kbn/data-plugin/public'; import { DataView, DataViewField } from '@kbn/data-views-plugin/public'; import { AggregateQuery, Filter, Query, TimeRange } from '@kbn/es-query'; import { PublishesDataViews, PublishingSubject } from '@kbn/presentation-publishing'; -import { combineLatest, lastValueFrom, Observable, of, startWith, switchMap, tap } from 'rxjs'; import { apiPublishesReload } from '@kbn/presentation-publishing/interfaces/fetch/publishes_reload'; +import { Observable, combineLatest, lastValueFrom, of, startWith, switchMap, tap } from 'rxjs'; +import { dataService } from '../../../../services/kibana_services'; import { ControlFetchContext } from '../../../control_group/control_fetch'; import { ControlGroupApi } from '../../../control_group/types'; export function minMax$({ controlFetch$, controlGroupApi, - data, dataViews$, fieldName$, setIsLoading, }: { controlFetch$: Observable; controlGroupApi: ControlGroupApi; - data: DataPublicPluginStart; dataViews$: PublishesDataViews['dataViews']; fieldName$: PublishingSubject; setIsLoading: (isLoading: boolean) => void; @@ -60,7 +58,6 @@ export function minMax$({ prevRequestAbortController = abortController; return await getMinMax({ abortSignal: abortController.signal, - data, dataView, field: dataViewField, ...controlFetchContext, @@ -77,7 +74,6 @@ export function minMax$({ export async function getMinMax({ abortSignal, - data, dataView, field, filters, @@ -85,20 +81,19 @@ export async function getMinMax({ timeRange, }: { abortSignal: AbortSignal; - data: DataPublicPluginStart; dataView: DataView; field: DataViewField; filters?: Filter[]; query?: Query | AggregateQuery; timeRange?: TimeRange; }): Promise<{ min: number | undefined; max: number | undefined }> { - const searchSource = await data.search.searchSource.create(); + const searchSource = await dataService.search.searchSource.create(); searchSource.setField('size', 0); searchSource.setField('index', dataView); const allFilters = filters ? [...filters] : []; if (timeRange) { - const timeFilter = data.query.timefilter.timefilter.createFilter(dataView, timeRange); + const timeFilter = dataService.query.timefilter.timefilter.createFilter(dataView, timeRange); if (timeFilter) allFilters.push(timeFilter); } if (allFilters.length) { diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/register_range_slider_control.ts b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/register_range_slider_control.ts index 4f77fc3bac7e4..0e1c0fd925792 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/register_range_slider_control.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/range_slider/register_range_slider_control.ts @@ -7,22 +7,17 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import type { CoreSetup } from '@kbn/core/public'; -import type { ControlsPluginStartDeps } from '../../../../types'; -import { registerControlFactory } from '../../../control_factory_registry'; import { RANGE_SLIDER_CONTROL } from '../../../../../common'; +import { untilPluginStartServicesReady } from '../../../../services/kibana_services'; +import { registerControlFactory } from '../../../control_factory_registry'; -export function registerRangeSliderControl(coreSetup: CoreSetup) { +export function registerRangeSliderControl() { registerControlFactory(RANGE_SLIDER_CONTROL, async () => { - const [{ getRangesliderControlFactory }, [coreStart, depsStart]] = await Promise.all([ + const [{ getRangesliderControlFactory }] = await Promise.all([ import('./get_range_slider_control_factory'), - coreSetup.getStartServices(), + untilPluginStartServicesReady(), ]); - return getRangesliderControlFactory({ - core: coreStart, - data: depsStart.data, - dataViews: depsStart.data.dataViews, - }); + return getRangesliderControlFactory(); }); } diff --git a/src/plugins/controls/public/react_controls/controls/data_controls/types.ts b/src/plugins/controls/public/react_controls/controls/data_controls/types.ts index 9eac141642402..89912e6eabb03 100644 --- a/src/plugins/controls/public/react_controls/controls/data_controls/types.ts +++ b/src/plugins/controls/public/react_controls/controls/data_controls/types.ts @@ -7,10 +7,7 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { CoreStart } from '@kbn/core/public'; -import { DataPublicPluginStart } from '@kbn/data-plugin/public'; import { DataViewField } from '@kbn/data-views-plugin/common'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; import { FieldFormatConvertFunction } from '@kbn/field-formats-plugin/common'; import { HasEditCapabilities, @@ -62,12 +59,6 @@ export const isDataControlFactory = ( return typeof (factory as DataControlFactory).isFieldCompatible === 'function'; }; -export interface DataControlServices { - core: CoreStart; - data: DataPublicPluginStart; - dataViews: DataViewsPublicPluginStart; -} - interface DataControlField { field: DataViewField; compatibleControlTypes: string[]; diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_time_range_meta.ts b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_time_range_meta.ts index 1cccb264d19e7..5c84cfbdef508 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_time_range_meta.ts +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_time_range_meta.ts @@ -9,6 +9,7 @@ import { EuiRangeTick } from '@elastic/eui'; import { TimeRange } from '@kbn/es-query'; +import { coreServices, dataService } from '../../../services/kibana_services'; import { FROM_INDEX, getStepSize, @@ -17,7 +18,6 @@ import { roundUpToNextStepSizeFactor, TO_INDEX, } from './time_utils'; -import { Services } from './types'; export interface TimeRangeMeta { format: string; @@ -29,12 +29,9 @@ export interface TimeRangeMeta { timeRangeMin: number; } -export function getTimeRangeMeta( - timeRange: TimeRange | undefined, - services: Services -): TimeRangeMeta { - const nextBounds = timeRangeToBounds(timeRange ?? getDefaultTimeRange(services), services); - const ticks = getTicks(nextBounds[FROM_INDEX], nextBounds[TO_INDEX], getTimezone(services)); +export function getTimeRangeMeta(timeRange: TimeRange | undefined): TimeRangeMeta { + const nextBounds = timeRangeToBounds(timeRange ?? getDefaultTimeRange()); + const ticks = getTicks(nextBounds[FROM_INDEX], nextBounds[TO_INDEX], getTimezone()); const { format, stepSize } = getStepSize(ticks); return { format, @@ -47,17 +44,17 @@ export function getTimeRangeMeta( }; } -export function getTimezone(services: Services) { - return services.core.uiSettings.get('dateFormat:tz', 'Browser'); +export function getTimezone() { + return coreServices.uiSettings.get('dateFormat:tz', 'Browser'); } -function getDefaultTimeRange(services: Services) { - const defaultTimeRange = services.core.uiSettings.get('timepicker:timeDefaults'); +function getDefaultTimeRange() { + const defaultTimeRange = coreServices.uiSettings.get('timepicker:timeDefaults'); return defaultTimeRange ? defaultTimeRange : { from: 'now-15m', to: 'now' }; } -function timeRangeToBounds(timeRange: TimeRange, services: Services): [number, number] { - const timeRangeBounds = services.data.query.timefilter.timefilter.calculateBounds(timeRange); +function timeRangeToBounds(timeRange: TimeRange): [number, number] { + const timeRangeBounds = dataService.query.timefilter.timefilter.calculateBounds(timeRange); return timeRangeBounds.min === undefined || timeRangeBounds.max === undefined ? [Date.now() - 1000 * 60 * 15, Date.now()] : [timeRangeBounds.min.valueOf(), timeRangeBounds.max.valueOf()]; diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.test.tsx b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.test.tsx index 12381ad83c407..d4b8ff6c13461 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.test.tsx +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.test.tsx @@ -7,14 +7,15 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { coreMock } from '@kbn/core/public/mocks'; -import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; +import React from 'react'; +import { BehaviorSubject } from 'rxjs'; + import dateMath from '@kbn/datemath'; import { TimeRange } from '@kbn/es-query'; import { StateComparators } from '@kbn/presentation-publishing'; import { fireEvent, render } from '@testing-library/react'; -import React from 'react'; -import { BehaviorSubject } from 'rxjs'; + +import { dataService } from '../../../services/kibana_services'; import { getMockedControlGroupApi } from '../mocks/control_mocks'; import { ControlApiRegistration } from '../types'; import { getTimesliderControlFactory } from './get_timeslider_control_factory'; @@ -28,18 +29,14 @@ describe('TimesliderControlApi', () => { }; const controlGroupApi = getMockedControlGroupApi(dashboardApi); - const dataStartServiceMock = dataPluginMock.createStartContract(); - dataStartServiceMock.query.timefilter.timefilter.calculateBounds = (timeRange: TimeRange) => { + dataService.query.timefilter.timefilter.calculateBounds = (timeRange: TimeRange) => { const now = new Date(); return { min: dateMath.parse(timeRange.from, { forceNow: now }), max: dateMath.parse(timeRange.to, { roundUp: true, forceNow: now }), }; }; - const factory = getTimesliderControlFactory({ - core: coreMock.createStart(), - data: dataStartServiceMock, - }); + const factory = getTimesliderControlFactory(); let comparators: StateComparators | undefined; function buildApiMock( api: ControlApiRegistration, diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.tsx b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.tsx index 20baf8fb545e1..cfc8e50bee1b5 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.tsx +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/get_timeslider_control_factory.tsx @@ -36,22 +36,23 @@ import { roundDownToNextStepSizeFactor, roundUpToNextStepSizeFactor, } from './time_utils'; -import { Services, Timeslice, TimesliderControlApi, TimesliderControlState } from './types'; +import { Timeslice, TimesliderControlApi, TimesliderControlState } from './types'; const displayName = i18n.translate('controls.timesliderControl.displayName', { defaultMessage: 'Time slider', }); -export const getTimesliderControlFactory = ( - services: Services -): ControlFactory => { +export const getTimesliderControlFactory = (): ControlFactory< + TimesliderControlState, + TimesliderControlApi +> => { return { type: TIME_SLIDER_CONTROL, getIconType: () => 'search', getDisplayName: () => displayName, buildControl: async (initialState, buildApi, uuid, controlGroupApi) => { const { timeRangeMeta$, formatDate, cleanupTimeRangeSubscription } = - initTimeRangeSubscription(controlGroupApi, services); + initTimeRangeSubscription(controlGroupApi); const timeslice$ = new BehaviorSubject<[number, number] | undefined>(undefined); const isAnchored$ = new BehaviorSubject(initialState.isAnchored); const isPopoverOpen$ = new BehaviorSubject(false); diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/init_time_range_subscription.ts b/src/plugins/controls/public/react_controls/controls/timeslider_control/init_time_range_subscription.ts index 7b4a2deb9f0d1..7934e9deaa9b4 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/init_time_range_subscription.ts +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/init_time_range_subscription.ts @@ -14,26 +14,23 @@ import moment from 'moment'; import { BehaviorSubject, skip } from 'rxjs'; import { getTimeRangeMeta, getTimezone, TimeRangeMeta } from './get_time_range_meta'; import { getMomentTimezone } from './time_utils'; -import { Services } from './types'; -export function initTimeRangeSubscription(controlGroupApi: unknown, services: Services) { +export function initTimeRangeSubscription(controlGroupApi: unknown) { const timeRange$ = apiHasParentApi(controlGroupApi) && apiPublishesTimeRange(controlGroupApi.parentApi) ? controlGroupApi.parentApi.timeRange$ : new BehaviorSubject(undefined); - const timeRangeMeta$ = new BehaviorSubject( - getTimeRangeMeta(timeRange$.value, services) - ); + const timeRangeMeta$ = new BehaviorSubject(getTimeRangeMeta(timeRange$.value)); const timeRangeSubscription = timeRange$.pipe(skip(1)).subscribe((timeRange) => { - timeRangeMeta$.next(getTimeRangeMeta(timeRange, services)); + timeRangeMeta$.next(getTimeRangeMeta(timeRange)); }); return { timeRangeMeta$, formatDate: (epoch: number) => { return moment - .tz(epoch, getMomentTimezone(getTimezone(services))) + .tz(epoch, getMomentTimezone(getTimezone())) .locale(i18n.getLocale()) .format(timeRangeMeta$.value.format); }, diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/register_timeslider_control.ts b/src/plugins/controls/public/react_controls/controls/timeslider_control/register_timeslider_control.ts index 8fbf23305820f..338a52631c931 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/register_timeslider_control.ts +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/register_timeslider_control.ts @@ -7,20 +7,16 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import type { CoreSetup } from '@kbn/core/public'; -import type { ControlsPluginStartDeps } from '../../../types'; -import { registerControlFactory } from '../../control_factory_registry'; import { TIME_SLIDER_CONTROL } from '../../../../common'; +import { untilPluginStartServicesReady } from '../../../services/kibana_services'; +import { registerControlFactory } from '../../control_factory_registry'; -export function registerTimeSliderControl(coreSetup: CoreSetup) { +export function registerTimeSliderControl() { registerControlFactory(TIME_SLIDER_CONTROL, async () => { - const [{ getTimesliderControlFactory }, [coreStart, depsStart]] = await Promise.all([ + const [{ getTimesliderControlFactory }] = await Promise.all([ import('./get_timeslider_control_factory'), - coreSetup.getStartServices(), + untilPluginStartServicesReady(), ]); - return getTimesliderControlFactory({ - core: coreStart, - data: depsStart.data, - }); + return getTimesliderControlFactory(); }); } diff --git a/src/plugins/controls/public/react_controls/controls/timeslider_control/types.ts b/src/plugins/controls/public/react_controls/controls/timeslider_control/types.ts index 702d02ae9accc..634e0351e77eb 100644 --- a/src/plugins/controls/public/react_controls/controls/timeslider_control/types.ts +++ b/src/plugins/controls/public/react_controls/controls/timeslider_control/types.ts @@ -7,8 +7,6 @@ * License v3.0 only", or the "Server Side Public License, v 1". */ -import { CoreStart } from '@kbn/core/public'; -import { DataPublicPluginStart } from '@kbn/data-plugin/public'; import type { PublishesPanelTitle, PublishesTimeslice } from '@kbn/presentation-publishing'; import type { DefaultControlState } from '../../../../common'; import type { DefaultControlApi } from '../types'; @@ -25,8 +23,3 @@ export interface TimesliderControlState extends DefaultControlState { export type TimesliderControlApi = DefaultControlApi & Pick & PublishesTimeslice; - -export interface Services { - core: CoreStart; - data: DataPublicPluginStart; -} diff --git a/src/plugins/controls/public/react_controls/controls/types.ts b/src/plugins/controls/public/react_controls/controls/types.ts index 85045f8bd70ba..ce4ad9f194fa3 100644 --- a/src/plugins/controls/public/react_controls/controls/types.ts +++ b/src/plugins/controls/public/react_controls/controls/types.ts @@ -40,15 +40,15 @@ export type DefaultControlApi = PublishesDataLoading & HasType & HasUniqueId & HasParentApi & { - // Can not use HasSerializableState interface - // HasSerializableState types serializeState as function returning 'MaybePromise' - // Controls serializeState is sync - serializeState: () => SerializedPanelState; - /** TODO: Make these non-public as part of https://github.com/elastic/kibana/issues/174961 */ setDataLoading: (loading: boolean) => void; setBlockingError: (error: Error | undefined) => void; grow: PublishingSubject; width: PublishingSubject; + + // Can not use HasSerializableState interface + // HasSerializableState types serializeState as function returning 'MaybePromise' + // Controls serializeState is sync + serializeState: () => SerializedPanelState; }; export type ControlApiRegistration = Omit< @@ -62,7 +62,6 @@ export type ControlApiInitialization; -// TODO: Move this to the Control plugin's setup contract export interface ControlFactory< State extends DefaultControlState = DefaultControlState, ControlApi extends DefaultControlApi = DefaultControlApi diff --git a/src/plugins/controls/public/react_controls/external_api/control_group_renderer.test.tsx b/src/plugins/controls/public/react_controls/external_api/control_group_renderer.test.tsx index 58269308f1846..e034ca817908e 100644 --- a/src/plugins/controls/public/react_controls/external_api/control_group_renderer.test.tsx +++ b/src/plugins/controls/public/react_controls/external_api/control_group_renderer.test.tsx @@ -9,26 +9,22 @@ import React from 'react'; -import { coreMock } from '@kbn/core/public/mocks'; -import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { embeddablePluginMock } from '@kbn/embeddable-plugin/public/mocks'; import { Filter } from '@kbn/es-query'; import { PublishesUnifiedSearch, PublishingSubject } from '@kbn/presentation-publishing'; import { act, render, waitFor } from '@testing-library/react'; import { ControlGroupRendererApi } from '.'; +import { CONTROL_GROUP_TYPE } from '../..'; import { getControlGroupEmbeddableFactory } from '../control_group/get_control_group_factory'; import { ControlGroupRenderer, ControlGroupRendererProps } from './control_group_renderer'; -import { CONTROL_GROUP_TYPE } from '../..'; type ParentApiType = PublishesUnifiedSearch & { unifiedSearchFilters$?: PublishingSubject; }; describe('control group renderer', () => { - const core = coreMock.createStart(); - const dataViews = dataViewPluginMocks.createStartContract(); - const factory = getControlGroupEmbeddableFactory({ core, dataViews }); + const factory = getControlGroupEmbeddableFactory(); const buildControlGroupSpy = jest.spyOn(factory, 'buildEmbeddable'); const mountControlGroupRenderer = async ( diff --git a/src/plugins/controls/public/services/controls/controls.stub.ts b/src/plugins/controls/public/services/controls/controls.stub.ts deleted file mode 100644 index 2e182998c9071..0000000000000 --- a/src/plugins/controls/public/services/controls/controls.stub.ts +++ /dev/null @@ -1,46 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlFactory, DefaultControlApi } from '../../react_controls/controls/types'; -import { ControlsServiceType } from './types'; - -export type ControlsServiceFactory = PluginServiceFactory; -export const controlsServiceFactory = () => getStubControlsService(); - -export const getStubControlsService = () => { - const controlsFactoriesMap: { [key: string]: ControlFactory } = {}; - - const mockRegisterControlFactory = async < - State extends object = object, - ApiType extends DefaultControlApi = DefaultControlApi - >( - controlType: string, - getFactory: () => Promise> - ) => { - controlsFactoriesMap[controlType] = (await getFactory()) as ControlFactory; - }; - - const mockGetControlFactory = < - State extends object = object, - ApiType extends DefaultControlApi = DefaultControlApi - >( - type: string - ) => { - return controlsFactoriesMap[type] as ControlFactory; - }; - - const getAllControlTypes = () => Object.keys(controlsFactoriesMap); - - return { - registerControlFactory: mockRegisterControlFactory, - getControlFactory: mockGetControlFactory, - getAllControlTypes, - }; -}; diff --git a/src/plugins/controls/public/services/controls/controls_service.ts b/src/plugins/controls/public/services/controls/controls_service.ts deleted file mode 100644 index c794c056a4f8d..0000000000000 --- a/src/plugins/controls/public/services/controls/controls_service.ts +++ /dev/null @@ -1,24 +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 { - getAllControlTypes, - getControlFactory, - registerControlFactory, -} from '../../react_controls/control_factory_registry'; -import { ControlsServiceType } from './types'; - -export const controlsServiceFactory = () => controlsService; - -// export controls service directly for use in plugin setup lifecycle -export const controlsService: ControlsServiceType = { - registerControlFactory, - getControlFactory, - getAllControlTypes, -}; diff --git a/src/plugins/controls/public/services/controls/types.ts b/src/plugins/controls/public/services/controls/types.ts deleted file mode 100644 index d9011819d815c..0000000000000 --- a/src/plugins/controls/public/services/controls/types.ts +++ /dev/null @@ -1,23 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { - getAllControlTypes, - getControlFactory, - registerControlFactory, -} from '../../react_controls/control_factory_registry'; - -export type ControlsServiceFactory = PluginServiceFactory; - -export interface ControlsServiceType { - registerControlFactory: typeof registerControlFactory; - getControlFactory: typeof getControlFactory; - getAllControlTypes: typeof getAllControlTypes; -} diff --git a/src/plugins/controls/public/services/core/core.stub.ts b/src/plugins/controls/public/services/core/core.stub.ts deleted file mode 100644 index 052ddf46129e2..0000000000000 --- a/src/plugins/controls/public/services/core/core.stub.ts +++ /dev/null @@ -1,24 +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 { analyticsServiceMock, coreMock, themeServiceMock } from '@kbn/core/public/mocks'; -import { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsCoreService } from './types'; - -export type CoreServiceFactory = PluginServiceFactory; - -export const coreServiceFactory: CoreServiceFactory = () => { - const corePluginMock = coreMock.createStart(); - return { - analytics: analyticsServiceMock.createAnalyticsServiceStart(), - theme: themeServiceMock.createSetupContract(), - i18n: corePluginMock.i18n, - notifications: corePluginMock.notifications, - }; -}; diff --git a/src/plugins/controls/public/services/core/core_service.ts b/src/plugins/controls/public/services/core/core_service.ts deleted file mode 100644 index 090784c32d806..0000000000000 --- a/src/plugins/controls/public/services/core/core_service.ts +++ /dev/null @@ -1,28 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsCoreService } from './types'; -import { ControlsPluginStartDeps } from '../../types'; - -export type CoreServiceFactory = KibanaPluginServiceFactory< - ControlsCoreService, - ControlsPluginStartDeps ->; - -export const coreServiceFactory: CoreServiceFactory = ({ coreStart }) => { - const { analytics, theme, i18n, notifications } = coreStart; - - return { - analytics, - theme, - i18n, - notifications, - }; -}; diff --git a/src/plugins/controls/public/services/core/types.ts b/src/plugins/controls/public/services/core/types.ts deleted file mode 100644 index 9424a490b3f3d..0000000000000 --- a/src/plugins/controls/public/services/core/types.ts +++ /dev/null @@ -1,17 +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 { CoreStart } from '@kbn/core/public'; - -export interface ControlsCoreService { - analytics: CoreStart['analytics']; - i18n: CoreStart['i18n']; - theme: CoreStart['theme']; - notifications: CoreStart['notifications']; -} diff --git a/src/plugins/controls/public/services/data/data.stub.ts b/src/plugins/controls/public/services/data/data.stub.ts deleted file mode 100644 index 5cd50a68768ef..0000000000000 --- a/src/plugins/controls/public/services/data/data.stub.ts +++ /dev/null @@ -1,31 +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 { of } from 'rxjs'; -import { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { DataPublicPluginStart } from '@kbn/data-plugin/public'; -import { ControlsDataService } from './types'; - -export type DataServiceFactory = PluginServiceFactory; -export const dataServiceFactory: DataServiceFactory = () => ({ - query: {} as unknown as DataPublicPluginStart['query'], - searchSource: { - create: () => ({ - setField: () => {}, - fetch$: () => - of({ - rawResponse: { aggregations: { minAgg: { value: 0 }, maxAgg: { value: 1000 } } }, - }), - }), - } as unknown as DataPublicPluginStart['search']['searchSource'], - timefilter: { - createFilter: () => {}, - } as unknown as DataPublicPluginStart['query']['timefilter']['timefilter'], - fetchFieldRange: () => Promise.resolve({ min: 0, max: 100 }), -}); diff --git a/src/plugins/controls/public/services/data/data_service.ts b/src/plugins/controls/public/services/data/data_service.ts deleted file mode 100644 index 84a36c2775dcd..0000000000000 --- a/src/plugins/controls/public/services/data/data_service.ts +++ /dev/null @@ -1,29 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsPluginStartDeps } from '../../types'; -import { ControlsDataService } from './types'; - -export type DataServiceFactory = KibanaPluginServiceFactory< - ControlsDataService, - ControlsPluginStartDeps ->; - -export const dataServiceFactory: DataServiceFactory = ({ startPlugins }) => { - const { - data: { query: queryPlugin, search }, - } = startPlugins; - - return { - query: queryPlugin, - searchSource: search.searchSource, - timefilter: queryPlugin.timefilter.timefilter, - }; -}; diff --git a/src/plugins/controls/public/services/data/types.ts b/src/plugins/controls/public/services/data/types.ts deleted file mode 100644 index 68a7553ee08dc..0000000000000 --- a/src/plugins/controls/public/services/data/types.ts +++ /dev/null @@ -1,15 +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 { DataPublicPluginStart } from '@kbn/data-plugin/public'; -export interface ControlsDataService { - query: DataPublicPluginStart['query']; - searchSource: DataPublicPluginStart['search']['searchSource']; - timefilter: DataPublicPluginStart['query']['timefilter']['timefilter']; -} diff --git a/src/plugins/controls/public/services/data_views/data_views.stub.ts b/src/plugins/controls/public/services/data_views/data_views.stub.ts deleted file mode 100644 index f2ffcf5f08a9d..0000000000000 --- a/src/plugins/controls/public/services/data_views/data_views.stub.ts +++ /dev/null @@ -1,52 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; -import { DataView } from '@kbn/data-views-plugin/common'; -import { ControlsDataViewsService } from './types'; - -export type DataViewsServiceFactory = PluginServiceFactory; - -let currentDataView: DataView | undefined; -export const injectStorybookDataView = (dataView?: DataView) => (currentDataView = dataView); - -export const dataViewsServiceFactory: DataViewsServiceFactory = () => ({ - get: ((dataViewId) => - new Promise((resolve, reject) => - setTimeout(() => { - if (!currentDataView) { - reject( - new Error( - 'mock DataViews service currentDataView is undefined, call injectStorybookDataView to set' - ) - ); - } else if (currentDataView.id === dataViewId) { - resolve(currentDataView); - } else { - reject( - new Error( - `mock DataViews service currentDataView.id: ${currentDataView.id} does not match requested dataViewId: ${dataViewId}` - ) - ); - } - }, 100) - ) as unknown) as DataViewsPublicPluginStart['get'], - getIdsWithTitle: (() => - new Promise((resolve) => - setTimeout(() => { - const idsWithTitle: Array<{ id: string | undefined; title: string }> = []; - if (currentDataView) { - idsWithTitle.push({ id: currentDataView.id, title: currentDataView.title }); - } - resolve(idsWithTitle); - }, 100) - ) as unknown) as DataViewsPublicPluginStart['getIdsWithTitle'], - getDefaultId: () => Promise.resolve(currentDataView?.id ?? null), -}); diff --git a/src/plugins/controls/public/services/data_views/data_views_service.ts b/src/plugins/controls/public/services/data_views/data_views_service.ts deleted file mode 100644 index 4ad4c0b8d2241..0000000000000 --- a/src/plugins/controls/public/services/data_views/data_views_service.ts +++ /dev/null @@ -1,29 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsPluginStartDeps } from '../../types'; -import { ControlsDataViewsService } from './types'; - -export type DataViewsServiceFactory = KibanaPluginServiceFactory< - ControlsDataViewsService, - ControlsPluginStartDeps ->; - -export const dataViewsServiceFactory: DataViewsServiceFactory = ({ startPlugins }) => { - const { - dataViews: { get, getIdsWithTitle, getDefaultId }, - } = startPlugins; - - return { - get, - getDefaultId, - getIdsWithTitle, - }; -}; diff --git a/src/plugins/controls/public/services/data_views/types.ts b/src/plugins/controls/public/services/data_views/types.ts deleted file mode 100644 index a204af439634e..0000000000000 --- a/src/plugins/controls/public/services/data_views/types.ts +++ /dev/null @@ -1,16 +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 { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; - -export interface ControlsDataViewsService { - get: DataViewsPublicPluginStart['get']; - getDefaultId: DataViewsPublicPluginStart['getDefaultId']; - getIdsWithTitle: DataViewsPublicPluginStart['getIdsWithTitle']; -} diff --git a/src/plugins/controls/public/services/embeddable/embeddable.stub.ts b/src/plugins/controls/public/services/embeddable/embeddable.stub.ts deleted file mode 100644 index 5f75b4e7b2d14..0000000000000 --- a/src/plugins/controls/public/services/embeddable/embeddable.stub.ts +++ /dev/null @@ -1,19 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { embeddablePluginMock } from '@kbn/embeddable-plugin/public/mocks'; -import { ControlsEmbeddableService } from './types'; - -export type EmbeddableServiceFactory = PluginServiceFactory; -export const embeddableServiceFactory: EmbeddableServiceFactory = () => { - const { doStart } = embeddablePluginMock.createInstance(); - const start = doStart(); - return { getEmbeddableFactory: start.getEmbeddableFactory }; -}; diff --git a/src/plugins/controls/public/services/embeddable/embeddable_service.ts b/src/plugins/controls/public/services/embeddable/embeddable_service.ts deleted file mode 100644 index 79c556f69c058..0000000000000 --- a/src/plugins/controls/public/services/embeddable/embeddable_service.ts +++ /dev/null @@ -1,23 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsEmbeddableService } from './types'; -import { ControlsPluginStartDeps } from '../../types'; - -export type EmbeddableServiceFactory = KibanaPluginServiceFactory< - ControlsEmbeddableService, - ControlsPluginStartDeps ->; - -export const embeddableServiceFactory: EmbeddableServiceFactory = ({ startPlugins }) => { - return { - getEmbeddableFactory: startPlugins.embeddable.getEmbeddableFactory, - }; -}; diff --git a/src/plugins/controls/public/services/embeddable/types.ts b/src/plugins/controls/public/services/embeddable/types.ts deleted file mode 100644 index 917f03fb55e9b..0000000000000 --- a/src/plugins/controls/public/services/embeddable/types.ts +++ /dev/null @@ -1,14 +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 { EmbeddableStart } from '@kbn/embeddable-plugin/public'; - -export interface ControlsEmbeddableService { - getEmbeddableFactory: EmbeddableStart['getEmbeddableFactory']; -} diff --git a/src/plugins/controls/public/services/http/http.stub.ts b/src/plugins/controls/public/services/http/http.stub.ts deleted file mode 100644 index ead893559b488..0000000000000 --- a/src/plugins/controls/public/services/http/http.stub.ts +++ /dev/null @@ -1,19 +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 { HttpResponse } from '@kbn/core/public'; -import { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsHTTPService } from './types'; - -type HttpServiceFactory = PluginServiceFactory; - -export const httpServiceFactory: HttpServiceFactory = () => ({ - get: async () => ({} as unknown as HttpResponse), - fetch: async () => ({} as unknown as HttpResponse), -}); diff --git a/src/plugins/controls/public/services/http/http_service.ts b/src/plugins/controls/public/services/http/http_service.ts deleted file mode 100644 index fac813ea92272..0000000000000 --- a/src/plugins/controls/public/services/http/http_service.ts +++ /dev/null @@ -1,27 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsHTTPService } from './types'; -import { ControlsPluginStartDeps } from '../../types'; - -export type HttpServiceFactory = KibanaPluginServiceFactory< - ControlsHTTPService, - ControlsPluginStartDeps ->; -export const httpServiceFactory: HttpServiceFactory = ({ coreStart }) => { - const { - http: { get, fetch }, - } = coreStart; - - return { - get, - fetch, - }; -}; diff --git a/src/plugins/controls/public/services/http/types.ts b/src/plugins/controls/public/services/http/types.ts deleted file mode 100644 index 0072bc0dacff0..0000000000000 --- a/src/plugins/controls/public/services/http/types.ts +++ /dev/null @@ -1,15 +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 { CoreSetup } from '@kbn/core/public'; - -export interface ControlsHTTPService { - get: CoreSetup['http']['get']; - fetch: CoreSetup['http']['fetch']; -} diff --git a/src/plugins/controls/public/services/index.ts b/src/plugins/controls/public/services/index.ts deleted file mode 100644 index a7cc0715e08d9..0000000000000 --- a/src/plugins/controls/public/services/index.ts +++ /dev/null @@ -1,10 +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". - */ - -export { pluginServices } from './plugin_services'; diff --git a/src/plugins/controls/public/services/kibana_services.ts b/src/plugins/controls/public/services/kibana_services.ts new file mode 100644 index 0000000000000..b9e5fadcecaa0 --- /dev/null +++ b/src/plugins/controls/public/services/kibana_services.ts @@ -0,0 +1,42 @@ +/* + * 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 { BehaviorSubject } from 'rxjs'; + +import { CoreStart } from '@kbn/core/public'; +import { DataPublicPluginStart } from '@kbn/data-plugin/public'; +import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; + +import { ControlsPluginStartDeps } from '../types'; + +export let coreServices: CoreStart; +export let dataService: DataPublicPluginStart; +export let dataViewsService: DataViewsPublicPluginStart; + +const servicesReady$ = new BehaviorSubject(false); + +export const setKibanaServices = (kibanaCore: CoreStart, deps: ControlsPluginStartDeps) => { + coreServices = kibanaCore; + dataService = deps.data; + dataViewsService = deps.dataViews; + + servicesReady$.next(true); +}; + +export const untilPluginStartServicesReady = () => { + if (servicesReady$.value) return Promise.resolve(); + return new Promise((resolve) => { + const subscription = servicesReady$.subscribe((isInitialized) => { + if (isInitialized) { + subscription.unsubscribe(); + resolve(); + } + }); + }); +}; diff --git a/src/plugins/controls/public/services/mocks.ts b/src/plugins/controls/public/services/mocks.ts new file mode 100644 index 0000000000000..231323c37a12a --- /dev/null +++ b/src/plugins/controls/public/services/mocks.ts @@ -0,0 +1,23 @@ +/* + * 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 { coreMock } from '@kbn/core/public/mocks'; +import { dataPluginMock } from '@kbn/data-plugin/public/mocks'; +import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; +import { uiActionsPluginMock } from '@kbn/ui-actions-plugin/public/mocks'; + +import { setKibanaServices } from './kibana_services'; + +export const setStubKibanaServices = () => { + setKibanaServices(coreMock.createStart(), { + data: dataPluginMock.createStartContract(), + dataViews: dataViewPluginMocks.createStartContract(), + uiActions: uiActionsPluginMock.createStartContract(), + }); +}; diff --git a/src/plugins/controls/public/services/overlays/overlays.stub.ts b/src/plugins/controls/public/services/overlays/overlays.stub.ts deleted file mode 100644 index d7938f5a8a3ce..0000000000000 --- a/src/plugins/controls/public/services/overlays/overlays.stub.ts +++ /dev/null @@ -1,33 +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 { - MountPoint, - OverlayFlyoutOpenOptions, - OverlayModalConfirmOptions, - OverlayRef, -} from '@kbn/core/public'; -import { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsOverlaysService } from './types'; - -type OverlaysServiceFactory = PluginServiceFactory; - -class StubRef implements OverlayRef { - public readonly onClose: Promise = Promise.resolve(); - - public close(): Promise { - return this.onClose; - } -} - -export const overlaysServiceFactory: OverlaysServiceFactory = () => ({ - openFlyout: (mount: MountPoint, options?: OverlayFlyoutOpenOptions) => new StubRef(), - openConfirm: (message: MountPoint | string, options?: OverlayModalConfirmOptions) => - Promise.resolve(true), -}); diff --git a/src/plugins/controls/public/services/overlays/overlays_service.ts b/src/plugins/controls/public/services/overlays/overlays_service.ts deleted file mode 100644 index b8e7309e4eb31..0000000000000 --- a/src/plugins/controls/public/services/overlays/overlays_service.ts +++ /dev/null @@ -1,27 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsPluginStartDeps } from '../../types'; -import { ControlsOverlaysService } from './types'; - -export type OverlaysServiceFactory = KibanaPluginServiceFactory< - ControlsOverlaysService, - ControlsPluginStartDeps ->; -export const overlaysServiceFactory: OverlaysServiceFactory = ({ coreStart }) => { - const { - overlays: { openFlyout, openConfirm }, - } = coreStart; - - return { - openFlyout, - openConfirm, - }; -}; diff --git a/src/plugins/controls/public/services/overlays/types.ts b/src/plugins/controls/public/services/overlays/types.ts deleted file mode 100644 index 7cb5fd2975549..0000000000000 --- a/src/plugins/controls/public/services/overlays/types.ts +++ /dev/null @@ -1,20 +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 { - MountPoint, - OverlayFlyoutOpenOptions, - OverlayModalConfirmOptions, - OverlayRef, -} from '@kbn/core/public'; - -export interface ControlsOverlaysService { - openFlyout(mount: MountPoint, options?: OverlayFlyoutOpenOptions): OverlayRef; - openConfirm(message: MountPoint | string, options?: OverlayModalConfirmOptions): Promise; -} diff --git a/src/plugins/controls/public/services/plugin_services.stub.ts b/src/plugins/controls/public/services/plugin_services.stub.ts deleted file mode 100644 index 1e7b3982f88cc..0000000000000 --- a/src/plugins/controls/public/services/plugin_services.stub.ts +++ /dev/null @@ -1,54 +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 { - PluginServiceProvider, - PluginServiceProviders, - PluginServiceRegistry, - PluginServices, -} from '@kbn/presentation-util-plugin/public'; - -import { ControlsPluginStart } from '../types'; -import { ControlsServices } from './types'; - -import { controlsServiceFactory } from './controls/controls.stub'; -import { coreServiceFactory } from './core/core.stub'; -import { dataServiceFactory } from './data/data.stub'; -import { dataViewsServiceFactory } from './data_views/data_views.stub'; -import { embeddableServiceFactory } from './embeddable/embeddable.stub'; -import { httpServiceFactory } from './http/http.stub'; -import { overlaysServiceFactory } from './overlays/overlays.stub'; -import { settingsServiceFactory } from './settings/settings.stub'; -import { unifiedSearchServiceFactory } from './unified_search/unified_search.stub'; -import { storageServiceFactory } from './storage/storage_service.stub'; - -export const providers: PluginServiceProviders = { - embeddable: new PluginServiceProvider(embeddableServiceFactory), - controls: new PluginServiceProvider(controlsServiceFactory), - data: new PluginServiceProvider(dataServiceFactory), - dataViews: new PluginServiceProvider(dataViewsServiceFactory), - http: new PluginServiceProvider(httpServiceFactory), - overlays: new PluginServiceProvider(overlaysServiceFactory), - settings: new PluginServiceProvider(settingsServiceFactory), - core: new PluginServiceProvider(coreServiceFactory), - storage: new PluginServiceProvider(storageServiceFactory), - unifiedSearch: new PluginServiceProvider(unifiedSearchServiceFactory), -}; - -export const pluginServices = new PluginServices(); - -export const registry = new PluginServiceRegistry(providers); - -export const getStubPluginServices = (): ControlsPluginStart => { - pluginServices.setRegistry(registry.start({})); - return { - getControlFactory: pluginServices.getServices().controls.getControlFactory, - getAllControlTypes: pluginServices.getServices().controls.getAllControlTypes, - }; -}; diff --git a/src/plugins/controls/public/services/plugin_services.ts b/src/plugins/controls/public/services/plugin_services.ts deleted file mode 100644 index d0d2552871173..0000000000000 --- a/src/plugins/controls/public/services/plugin_services.ts +++ /dev/null @@ -1,52 +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 { - KibanaPluginServiceParams, - PluginServiceProvider, - PluginServiceProviders, - PluginServiceRegistry, - PluginServices, -} from '@kbn/presentation-util-plugin/public'; -import { ControlsPluginStartDeps } from '../types'; -import { ControlsServices } from './types'; - -import { controlsServiceFactory } from './controls/controls_service'; -import { coreServiceFactory } from './core/core_service'; -import { dataServiceFactory } from './data/data_service'; -import { dataViewsServiceFactory } from './data_views/data_views_service'; -import { embeddableServiceFactory } from './embeddable/embeddable_service'; -import { httpServiceFactory } from './http/http_service'; -import { overlaysServiceFactory } from './overlays/overlays_service'; -import { settingsServiceFactory } from './settings/settings_service'; -import { controlsStorageServiceFactory } from './storage/storage_service'; -import { unifiedSearchServiceFactory } from './unified_search/unified_search_service'; - -export const providers: PluginServiceProviders< - ControlsServices, - KibanaPluginServiceParams -> = { - controls: new PluginServiceProvider(controlsServiceFactory), - data: new PluginServiceProvider(dataServiceFactory), - dataViews: new PluginServiceProvider(dataViewsServiceFactory), - embeddable: new PluginServiceProvider(embeddableServiceFactory), - http: new PluginServiceProvider(httpServiceFactory), - overlays: new PluginServiceProvider(overlaysServiceFactory), - settings: new PluginServiceProvider(settingsServiceFactory), - storage: new PluginServiceProvider(controlsStorageServiceFactory), - core: new PluginServiceProvider(coreServiceFactory), - unifiedSearch: new PluginServiceProvider(unifiedSearchServiceFactory), -}; - -export const pluginServices = new PluginServices(); - -export const registry = new PluginServiceRegistry< - ControlsServices, - KibanaPluginServiceParams ->(providers); diff --git a/src/plugins/controls/public/services/settings/settings.stub.ts b/src/plugins/controls/public/services/settings/settings.stub.ts deleted file mode 100644 index 6ee5bdce4f2f4..0000000000000 --- a/src/plugins/controls/public/services/settings/settings.stub.ts +++ /dev/null @@ -1,18 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsSettingsService } from './types'; - -export type SettingsServiceFactory = PluginServiceFactory; -export const settingsServiceFactory: SettingsServiceFactory = () => ({ - getTimezone: () => 'Browser', - getDateFormat: () => 'MMM D, YYYY @ HH:mm:ss.SSS', - getDefaultTimeRange: () => ({ from: 'now-15m', to: 'now' }), -}); diff --git a/src/plugins/controls/public/services/settings/settings_service.ts b/src/plugins/controls/public/services/settings/settings_service.ts deleted file mode 100644 index e5f8751503a67..0000000000000 --- a/src/plugins/controls/public/services/settings/settings_service.ts +++ /dev/null @@ -1,32 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsSettingsService } from './types'; -import { ControlsPluginStartDeps } from '../../types'; - -export type SettingsServiceFactory = KibanaPluginServiceFactory< - ControlsSettingsService, - ControlsPluginStartDeps ->; - -export const settingsServiceFactory: SettingsServiceFactory = ({ coreStart }) => { - return { - getDateFormat: () => { - return coreStart.uiSettings.get('dateFormat', 'MMM D, YYYY @ HH:mm:ss.SSS'); - }, - getTimezone: () => { - return coreStart.uiSettings.get('dateFormat:tz', 'Browser'); - }, - getDefaultTimeRange: () => { - const defaultTimeRange = coreStart.uiSettings.get('timepicker:timeDefaults'); - return defaultTimeRange ? defaultTimeRange : { from: 'now-15m', to: 'now' }; - }, - }; -}; diff --git a/src/plugins/controls/public/services/settings/types.ts b/src/plugins/controls/public/services/settings/types.ts deleted file mode 100644 index f8b29adeb85a7..0000000000000 --- a/src/plugins/controls/public/services/settings/types.ts +++ /dev/null @@ -1,16 +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 { TimeRange } from '@kbn/es-query'; - -export interface ControlsSettingsService { - getTimezone: () => string; - getDateFormat: () => string; - getDefaultTimeRange: () => TimeRange; -} diff --git a/src/plugins/controls/public/services/storage/storage_service.stub.ts b/src/plugins/controls/public/services/storage/storage_service.stub.ts deleted file mode 100644 index 389d804b51bb0..0000000000000 --- a/src/plugins/controls/public/services/storage/storage_service.stub.ts +++ /dev/null @@ -1,20 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsStorageService } from './types'; - -type StorageServiceFactory = PluginServiceFactory; - -export const storageServiceFactory: StorageServiceFactory = () => { - return { - getShowInvalidSelectionWarning: () => false, - setShowInvalidSelectionWarning: (value: boolean) => null, - }; -}; diff --git a/src/plugins/controls/public/services/storage/storage_service.ts b/src/plugins/controls/public/services/storage/storage_service.ts deleted file mode 100644 index 9f0403c505e74..0000000000000 --- a/src/plugins/controls/public/services/storage/storage_service.ts +++ /dev/null @@ -1,31 +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 { Storage } from '@kbn/kibana-utils-plugin/public'; -import { ControlsStorageService } from './types'; - -const STORAGE_KEY = 'controls:showInvalidSelectionWarning'; - -class StorageService implements ControlsStorageService { - private storage: Storage; - - constructor() { - this.storage = new Storage(localStorage); - } - - getShowInvalidSelectionWarning = () => { - return this.storage.get(STORAGE_KEY); - }; - - setShowInvalidSelectionWarning = (value: boolean) => { - this.storage.set(STORAGE_KEY, value); - }; -} - -export const controlsStorageServiceFactory = () => new StorageService(); diff --git a/src/plugins/controls/public/services/storage/types.ts b/src/plugins/controls/public/services/storage/types.ts deleted file mode 100644 index 2d1e8b08e8364..0000000000000 --- a/src/plugins/controls/public/services/storage/types.ts +++ /dev/null @@ -1,13 +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". - */ - -export interface ControlsStorageService { - getShowInvalidSelectionWarning: () => boolean; - setShowInvalidSelectionWarning: (value: boolean) => void; -} diff --git a/src/plugins/controls/public/services/types.ts b/src/plugins/controls/public/services/types.ts deleted file mode 100644 index c38ad6b64fac6..0000000000000 --- a/src/plugins/controls/public/services/types.ts +++ /dev/null @@ -1,35 +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 { ControlsServiceType } from './controls/types'; -import { ControlsCoreService } from './core/types'; -import { ControlsDataService } from './data/types'; -import { ControlsDataViewsService } from './data_views/types'; -import { ControlsEmbeddableService } from './embeddable/types'; -import { ControlsHTTPService } from './http/types'; -import { ControlsOverlaysService } from './overlays/types'; -import { ControlsSettingsService } from './settings/types'; -import { ControlsStorageService } from './storage/types'; -import { ControlsUnifiedSearchService } from './unified_search/types'; - -export interface ControlsServices { - // dependency services - dataViews: ControlsDataViewsService; - overlays: ControlsOverlaysService; - embeddable: ControlsEmbeddableService; - data: ControlsDataService; - unifiedSearch: ControlsUnifiedSearchService; - http: ControlsHTTPService; - settings: ControlsSettingsService; - core: ControlsCoreService; - - // controls plugin's own services - controls: ControlsServiceType; - storage: ControlsStorageService; -} diff --git a/src/plugins/controls/public/services/unified_search/types.ts b/src/plugins/controls/public/services/unified_search/types.ts deleted file mode 100644 index 28aa8e05feb2d..0000000000000 --- a/src/plugins/controls/public/services/unified_search/types.ts +++ /dev/null @@ -1,14 +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 { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public'; - -export interface ControlsUnifiedSearchService { - autocomplete: UnifiedSearchPublicPluginStart['autocomplete']; -} diff --git a/src/plugins/controls/public/services/unified_search/unified_search.stub.ts b/src/plugins/controls/public/services/unified_search/unified_search.stub.ts deleted file mode 100644 index c7b1959c8bbc0..0000000000000 --- a/src/plugins/controls/public/services/unified_search/unified_search.stub.ts +++ /dev/null @@ -1,27 +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 { PluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { DataViewField } from '@kbn/data-views-plugin/common'; -import { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public'; - -import { ControlsUnifiedSearchService } from './types'; - -let valueSuggestionMethod = ({ field, query }: { field: DataViewField; query: string }) => - Promise.resolve(['storybook', 'default', 'values']); -export const replaceValueSuggestionMethod = ( - newMethod: ({ field, query }: { field: DataViewField; query: string }) => Promise -) => (valueSuggestionMethod = newMethod); - -export type UnifiedSearchServiceFactory = PluginServiceFactory; -export const unifiedSearchServiceFactory: UnifiedSearchServiceFactory = () => ({ - autocomplete: { - getValueSuggestions: valueSuggestionMethod, - } as unknown as UnifiedSearchPublicPluginStart['autocomplete'], -}); diff --git a/src/plugins/controls/public/services/unified_search/unified_search_service.ts b/src/plugins/controls/public/services/unified_search/unified_search_service.ts deleted file mode 100644 index 45d10cfa9ac7d..0000000000000 --- a/src/plugins/controls/public/services/unified_search/unified_search_service.ts +++ /dev/null @@ -1,27 +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 { KibanaPluginServiceFactory } from '@kbn/presentation-util-plugin/public'; -import { ControlsPluginStartDeps } from '../../types'; -import { ControlsUnifiedSearchService } from './types'; - -export type UnifiedSearchServiceFactory = KibanaPluginServiceFactory< - ControlsUnifiedSearchService, - ControlsPluginStartDeps ->; - -export const unifiedSearchServiceFactory: UnifiedSearchServiceFactory = ({ startPlugins }) => { - const { - unifiedSearch: { autocomplete }, - } = startPlugins; - - return { - autocomplete, - }; -}; diff --git a/src/plugins/controls/public/types.ts b/src/plugins/controls/public/types.ts index 2ecbd38763603..bed3260bb4401 100644 --- a/src/plugins/controls/public/types.ts +++ b/src/plugins/controls/public/types.ts @@ -9,11 +9,8 @@ import { DataPublicPluginStart } from '@kbn/data-plugin/public'; import { DataViewsPublicPluginStart } from '@kbn/data-views-plugin/public'; -import { EmbeddableSetup, EmbeddableStart } from '@kbn/embeddable-plugin/public'; +import { EmbeddableSetup } from '@kbn/embeddable-plugin/public'; import { UiActionsStart } from '@kbn/ui-actions-plugin/public'; -import { UnifiedSearchPublicPluginStart } from '@kbn/unified-search-plugin/public'; - -import { ControlsServiceType } from './services/controls/types'; export interface CanClearSelections { clearSelections: () => void; @@ -26,22 +23,11 @@ export const isClearableControl = (control: unknown): control is CanClearSelecti /** * Plugin types */ -export interface ControlsPluginSetup { - registerControlFactory: ControlsServiceType['registerControlFactory']; -} - -export interface ControlsPluginStart { - getControlFactory: ControlsServiceType['getControlFactory']; - getAllControlTypes: ControlsServiceType['getAllControlTypes']; -} - export interface ControlsPluginSetupDeps { embeddable: EmbeddableSetup; } export interface ControlsPluginStartDeps { uiActions: UiActionsStart; - embeddable: EmbeddableStart; data: DataPublicPluginStart; dataViews: DataViewsPublicPluginStart; - unifiedSearch: UnifiedSearchPublicPluginStart; } diff --git a/src/plugins/controls/server/control_group/control_group_persistence.ts b/src/plugins/controls/server/control_group/control_group_persistence.ts index eb63b28ccecba..e90aa850c6d1a 100644 --- a/src/plugins/controls/server/control_group/control_group_persistence.ts +++ b/src/plugins/controls/server/control_group/control_group_persistence.ts @@ -10,7 +10,7 @@ import { SerializableRecord } from '@kbn/utility-types'; import { - DEFAULT_CONTROL_STYLE, + DEFAULT_CONTROL_LABEL_POSITION, type ControlGroupRuntimeState, type ControlGroupSerializedState, type ControlPanelState, @@ -19,7 +19,7 @@ import { export const getDefaultControlGroupState = (): SerializableControlGroupState => ({ panels: {}, - labelPosition: DEFAULT_CONTROL_STYLE, + labelPosition: DEFAULT_CONTROL_LABEL_POSITION, chainingSystem: 'HIERARCHICAL', autoApplySelections: true, ignoreParentSettings: { diff --git a/src/plugins/controls/server/options_list/options_list_cluster_settings_route.ts b/src/plugins/controls/server/options_list/options_list_cluster_settings_route.ts index f51b9a5b5b62c..04b0aaa3e6f78 100644 --- a/src/plugins/controls/server/options_list/options_list_cluster_settings_route.ts +++ b/src/plugins/controls/server/options_list/options_list_cluster_settings_route.ts @@ -15,7 +15,7 @@ export const setupOptionsListClusterSettingsRoute = ({ http }: CoreSetup) => { router.versioned .get({ access: 'internal', - path: '/internal/controls/optionsList/getExpensiveQueriesSetting', + path: '/internal/controls/getExpensiveQueriesSetting', }) .addVersion( { diff --git a/src/plugins/controls/tsconfig.json b/src/plugins/controls/tsconfig.json index fc9d6572ccf2f..abcafa291358e 100644 --- a/src/plugins/controls/tsconfig.json +++ b/src/plugins/controls/tsconfig.json @@ -35,7 +35,6 @@ "@kbn/presentation-containers", "@kbn/presentation-publishing", "@kbn/content-management-utils", - "@kbn/core-lifecycle-browser", "@kbn/field-formats-plugin", "@kbn/presentation-panel-plugin", "@kbn/shared-ux-utility"