From d43c5c618c65009105adc85fedebc2586b228a6f Mon Sep 17 00:00:00 2001 From: Jean-Louis Leysens Date: Thu, 14 Nov 2019 10:12:18 +0100 Subject: [PATCH 1/9] [Rollup] Fix for clone job workflow (#50501) * First iteration of fix for clone job workflow * Second iteration of fix, previous had race condition :gasp: * Slight revision to logic and added test for wizard with rollup job after index pattern changed --- .../helpers/job_clone.helpers.js | 10 +-- .../job_create_clone.test.js | 62 ++++++++++++++++++- .../sections/job_create/job_create.js | 25 ++++---- 3 files changed, 79 insertions(+), 18 deletions(-) diff --git a/x-pack/legacy/plugins/rollup/__jest__/client_integration/helpers/job_clone.helpers.js b/x-pack/legacy/plugins/rollup/__jest__/client_integration/helpers/job_clone.helpers.js index 48672a8bc13dd..b99eb44bee3b9 100644 --- a/x-pack/legacy/plugins/rollup/__jest__/client_integration/helpers/job_clone.helpers.js +++ b/x-pack/legacy/plugins/rollup/__jest__/client_integration/helpers/job_clone.helpers.js @@ -10,13 +10,13 @@ import { JobCreate } from '../../../public/crud_app/sections'; import { JOB_TO_CLONE } from './constants'; import { deserializeJob } from '../../../public/crud_app/services'; -const initTestBed = registerTestBed(JobCreate, { - store: createRollupJobsStore({ - cloneJob: { job: deserializeJob(JOB_TO_CLONE.jobs[0]) }, - }), -}); export const setup = props => { + const initTestBed = registerTestBed(JobCreate, { + store: createRollupJobsStore({ + cloneJob: { job: deserializeJob(JOB_TO_CLONE.jobs[0]) }, + }), + }); const testBed = initTestBed(props); const { component } = testBed; diff --git a/x-pack/legacy/plugins/rollup/__jest__/client_integration/job_create_clone.test.js b/x-pack/legacy/plugins/rollup/__jest__/client_integration/job_create_clone.test.js index 8a0b3159b34df..29d2d00163ad8 100644 --- a/x-pack/legacy/plugins/rollup/__jest__/client_integration/job_create_clone.test.js +++ b/x-pack/legacy/plugins/rollup/__jest__/client_integration/job_create_clone.test.js @@ -4,7 +4,7 @@ * you may not use this file except in compliance with the Elastic License. */ -import { setupEnvironment, pageHelpers } from './helpers'; +import { setupEnvironment, pageHelpers, nextTick } from './helpers'; import { JOB_TO_CLONE, JOB_CLONE_INDEX_PATTERN_CHECK } from './helpers/constants'; jest.mock('ui/new_platform'); @@ -134,4 +134,64 @@ describe('Cloning a rollup job through create job wizard', () => { expect(checkedCountActual).toBe(checkedCountExpected); }); }); + + it('should correctly reset defaults after index pattern changes', async () => { + // 1. Logistics + + // Sanity check for rollup job name, i.e., we are in clone mode. + expect(find('rollupJobName').props().value).toBe(jobConfig.id + '-copy'); + + // Changing the index pattern value after cloning a rollup job should update a number of values. + // On each view of the set up wizard we check for the expected state after this change. + form.setInputValue('rollupIndexPattern', 'test'); + // Fires off a network request. + await nextTick(); + + const { + groups: { + date_histogram: dateHistogram + }, + } = jobConfig; + + await actions.clickNextStep(); + + // 2. Date Histogram + + expect(exists('rollupJobCreateDateHistogramTitle')).toBe(true); + expect(find('rollupJobCreateDateFieldSelect').props().value).toBe(dateHistogram.field); + + await actions.clickNextStep(); + + // 3. Terms + + expect(exists('rollupJobCreateTermsTitle')).toBe(true); + const { tableCellsValues: tableCellValuesTerms } = table.getMetaData('rollupJobTermsFieldList'); + expect(tableCellValuesTerms[0][0]).toBe('No terms fields added'); + + await actions.clickNextStep(); + + // 4. Histogram + + expect(exists('rollupJobCreateHistogramTitle')).toBe(true); + const { tableCellsValues: tableCellValuesHisto } = table.getMetaData( + 'rollupJobHistogramFieldList' + ); + + expect(tableCellValuesHisto[0][0]).toBe('No histogram fields added'); + + await actions.clickNextStep(); + + // 5. Metrics + + expect(exists('rollupJobCreateMetricsTitle')).toBe(true); + const { rows: metricsRows } = table.getMetaData('rollupJobMetricsFieldList'); + // Empty placeholder value + expect(metricsRows.length).toBe(1); + + // 6. Review + + await actions.clickNextStep(); + + expect(exists('rollupJobCreateReviewTitle')).toBe(true); + }); }); diff --git a/x-pack/legacy/plugins/rollup/public/crud_app/sections/job_create/job_create.js b/x-pack/legacy/plugins/rollup/public/crud_app/sections/job_create/job_create.js index 1d7d0c1dd8dea..52968c22045df 100644 --- a/x-pack/legacy/plugins/rollup/public/crud_app/sections/job_create/job_create.js +++ b/x-pack/legacy/plugins/rollup/public/crud_app/sections/job_create/job_create.js @@ -125,13 +125,14 @@ export class JobCreateUi extends Component { const { clearCloneJob, jobToClone } = this.props; if (jobToClone) { clearCloneJob(); - this.requestIndexPatternValidation(); + this.requestIndexPatternValidation(false); } } componentDidUpdate(prevProps, prevState) { const indexPattern = this.getIndexPattern(); if (indexPattern !== this.getIndexPattern(prevState)) { + // If the user hasn't entered anything, then skip validation. if (!indexPattern || !indexPattern.trim()) { this.setState({ @@ -159,7 +160,7 @@ export class JobCreateUi extends Component { this.props.clearCreateJobErrors(); } - requestIndexPatternValidation = debounce(() => { + requestIndexPatternValidation = debounce((resetDefaults = true) => { const indexPattern = this.getIndexPattern(); const lastIndexPatternValidationTime = this.lastIndexPatternValidationTime = Date.now(); @@ -265,6 +266,16 @@ export class JobCreateUi extends Component { indexPatternDateFields.sort(); + if (resetDefaults) { + // Whenever the index pattern changes we default to the first date field if there is one. + this.onFieldsChange( + { + dateHistogramField: indexPatternDateFields.length ? indexPatternDateFields[0] : undefined, + }, + STEP_DATE_HISTOGRAM + ); + } + this.setState({ indexPatternAsyncErrors, indexPatternDateFields, @@ -273,16 +284,6 @@ export class JobCreateUi extends Component { indexPatternMetricsFields, isValidatingIndexPattern: false, }); - - if (!jobToClone) { - // Select first time field by default. - this.onFieldsChange( - { - dateHistogramField: indexPatternDateFields.length ? indexPatternDateFields[0] : null, - }, - STEP_DATE_HISTOGRAM - ); - } }).catch(error => { // We don't need to do anything if this component has been unmounted. if (!this._isMounted) { From 62d035390eb63234464e79b615e275dedc0e16f1 Mon Sep 17 00:00:00 2001 From: Joe Reuter Date: Thu, 14 Nov 2019 10:38:44 +0100 Subject: [PATCH 2/9] Shim dev tools (#49349) --- src/legacy/core_plugins/console/index.ts | 3 - .../application/containers/main/main.tsx | 4 +- .../console/np_ready/public/legacy.ts | 69 +------ .../console/np_ready/public/plugin.ts | 43 +++- .../console/public/quarantined/index.html | 3 - src/legacy/core_plugins/kibana/index.js | 2 +- .../kibana/public/dev_tools/_index.scss | 3 + .../kibana/public/dev_tools/application.tsx | 184 ++++++++++++++++++ .../dev_tools/directives/dev_tools_app.js | 50 ----- .../hacks/__tests__/hide_empty_tools.js | 59 ------ .../dev_tools/hacks/hide_empty_tools.js | 33 ---- .../kibana/public/dev_tools/index.js | 77 -------- .../public/dev_tools/index.ts} | 24 ++- .../dev_tools/partials/dev_tools_app.html | 22 --- .../kibana/public/dev_tools/plugin.ts | 71 +++++++ .../core_plugins/kibana/public/kibana.js | 1 - src/legacy/plugin_discovery/types.ts | 1 - .../new_platform/new_platform.karma_mock.js | 6 + .../ui/public/new_platform/new_platform.ts | 3 + src/plugins/dev_tools/README.md | 29 +++ src/plugins/dev_tools/kibana.json | 6 + .../dev_tools/public/index.ts} | 12 +- src/plugins/dev_tools/public/plugin.ts | 115 +++++++++++ x-pack/legacy/plugins/grokdebugger/index.js | 3 +- .../custom_patterns_input.js | 2 +- .../components/custom_patterns_input/index.js | 0 .../components/event_input/event_input.js | 2 +- .../components/event_input/index.js | 0 .../components/event_output/event_output.js | 0 .../components/event_output/index.js | 0 .../components/grok_debugger/grok_debugger.js | 2 +- .../components/grok_debugger/index.js | 0 .../components/pattern_input/index.js | 0 .../components/pattern_input/pattern_input.js | 4 +- .../plugins/grokdebugger/public/register.js | 33 ++++ .../plugins/grokdebugger/public/render_app.js | 22 +++ .../directives/grokdebugger/grokdebugger.js | 25 --- .../directives/grokdebugger/index.js | 7 - .../grokdebugger/grokdebugger_route.html | 3 - .../grokdebugger/grokdebugger_route.js | 40 ---- .../public/sections/grokdebugger/index.js | 7 - .../public/sections/grokdebugger/register.js | 22 --- .../grokdebugger_service.factory.js | 14 -- .../grokdebugger/grokdebugger_service.js | 11 +- .../public/services/grokdebugger/index.js | 7 - x-pack/legacy/plugins/searchprofiler/index.ts | 1 - .../plugins/searchprofiler/public/legacy.ts | 51 +---- .../searchprofiler/public/np_ready/plugin.ts | 21 +- .../plugins/searchprofiler/public/register.js | 20 -- .../translations/translations/ja-JP.json | 4 +- .../translations/translations/zh-CN.json | 4 +- .../feature_controls/dev_tools_security.ts | 4 +- .../feature_controls/dev_tools_spaces.ts | 2 +- 53 files changed, 581 insertions(+), 550 deletions(-) delete mode 100644 src/legacy/core_plugins/console/public/quarantined/index.html create mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/application.tsx delete mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/directives/dev_tools_app.js delete mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/hacks/__tests__/hide_empty_tools.js delete mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/hacks/hide_empty_tools.js delete mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/index.js rename src/legacy/core_plugins/{console/public/quarantined/hacks/register.js => kibana/public/dev_tools/index.ts} (68%) delete mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/partials/dev_tools_app.html create mode 100644 src/legacy/core_plugins/kibana/public/dev_tools/plugin.ts create mode 100644 src/plugins/dev_tools/README.md create mode 100644 src/plugins/dev_tools/kibana.json rename src/{legacy/ui/public/registry/dev_tools.js => plugins/dev_tools/public/index.ts} (77%) create mode 100644 src/plugins/dev_tools/public/plugin.ts rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/custom_patterns_input/custom_patterns_input.js (96%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/custom_patterns_input/index.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/event_input/event_input.js (94%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/event_input/index.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/event_output/event_output.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/event_output/index.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/grok_debugger/grok_debugger.js (98%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/grok_debugger/index.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/pattern_input/index.js (100%) rename x-pack/legacy/plugins/grokdebugger/public/{sections/grokdebugger => }/components/pattern_input/pattern_input.js (91%) create mode 100644 x-pack/legacy/plugins/grokdebugger/public/register.js create mode 100644 x-pack/legacy/plugins/grokdebugger/public/render_app.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/grokdebugger.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/index.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.html delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/index.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/register.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.factory.js delete mode 100644 x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/index.js delete mode 100644 x-pack/legacy/plugins/searchprofiler/public/register.js diff --git a/src/legacy/core_plugins/console/index.ts b/src/legacy/core_plugins/console/index.ts index 30a85f4e7d342..caef3ff6f99f3 100644 --- a/src/legacy/core_plugins/console/index.ts +++ b/src/legacy/core_plugins/console/index.ts @@ -56,7 +56,6 @@ export default function(kibana: any) { const npSrc = resolve(__dirname, 'np_ready/public'); let defaultVars: any; - const apps: any[] = []; return new kibana.Plugin({ id: 'console', require: ['elasticsearch'], @@ -181,8 +180,6 @@ export default function(kibana: any) { }, uiExports: { - apps, - hacks: ['plugins/console/quarantined/hacks/register'], devTools: [`${npSrc}/legacy`], styleSheetPaths: resolve(__dirname, 'public/quarantined/index.scss'), diff --git a/src/legacy/core_plugins/console/np_ready/public/application/containers/main/main.tsx b/src/legacy/core_plugins/console/np_ready/public/application/containers/main/main.tsx index 4e5afbdb5821e..518630c5a07c1 100644 --- a/src/legacy/core_plugins/console/np_ready/public/application/containers/main/main.tsx +++ b/src/legacy/core_plugins/console/np_ready/public/application/containers/main/main.tsx @@ -70,7 +70,7 @@ export function Main() { }; return ( - <> +
setShowSettings(false)} /> : null} {showHelp ? setShowHelp(false)} /> : null} - +
); } diff --git a/src/legacy/core_plugins/console/np_ready/public/legacy.ts b/src/legacy/core_plugins/console/np_ready/public/legacy.ts index 1a2d312823f6f..8c60ff23648be 100644 --- a/src/legacy/core_plugins/console/np_ready/public/legacy.ts +++ b/src/legacy/core_plugins/console/np_ready/public/legacy.ts @@ -24,80 +24,31 @@ import 'brace/mode/json'; import 'brace/mode/text'; /* eslint-disable @kbn/eslint/no-restricted-paths */ -import { toastNotifications as notifications } from 'ui/notify'; import { npSetup, npStart } from 'ui/new_platform'; -import uiRoutes from 'ui/routes'; -import { DOC_LINK_VERSION } from 'ui/documentation_links'; import { I18nContext } from 'ui/i18n'; import { ResizeChecker } from 'ui/resize_checker'; -import 'ui/capabilities/route_setup'; /* eslint-enable @kbn/eslint/no-restricted-paths */ -import template from '../../public/quarantined/index.html'; -import { App, AppUnmount, NotificationsSetup } from '../../../../../core/public'; - export interface XPluginSet { + devTools: DevToolsSetup; + feature_catalogue: FeatureCatalogueSetup; __LEGACY: { I18nContext: any; ResizeChecker: any; - docLinkVersion: string; }; } import { plugin } from '.'; +import { DevToolsSetup } from '../../../../../plugins/dev_tools/public'; +import { FeatureCatalogueSetup } from '../../../../../plugins/feature_catalogue/public'; const pluginInstance = plugin({} as any); -const anyObject = {} as any; - -uiRoutes.when('/dev_tools/console', { - requireUICapability: 'dev_tools.show', - controller: function RootController($scope) { - // Stub out this config for now... - $scope.topNavMenu = []; - - $scope.initReactApp = () => { - const targetElement = document.querySelector('#consoleRoot'); - if (!targetElement) { - const message = `Could not mount Console App!`; - npSetup.core.fatalErrors.add(message); - throw new Error(message); - } - - let unmount: AppUnmount | Promise; - - const mockedSetupCore = { - ...npSetup.core, - notifications: (notifications as unknown) as NotificationsSetup, - application: { - register(app: App): void { - try { - unmount = app.mount(anyObject, { element: targetElement, appBasePath: '' }); - } catch (e) { - npSetup.core.fatalErrors.add(e); - } - }, - registerMountContext() {}, - }, - }; - - pluginInstance.setup(mockedSetupCore, { - ...npSetup.plugins, - __LEGACY: { - I18nContext, - ResizeChecker, - docLinkVersion: DOC_LINK_VERSION, - }, - }); - pluginInstance.start(npStart.core); - - $scope.$on('$destroy', async () => { - if (unmount) { - const fn = await unmount; - fn(); - } - }); - }; +pluginInstance.setup(npSetup.core, { + ...npSetup.plugins, + __LEGACY: { + I18nContext, + ResizeChecker, }, - template, }); +pluginInstance.start(npStart.core); diff --git a/src/legacy/core_plugins/console/np_ready/public/plugin.ts b/src/legacy/core_plugins/console/np_ready/public/plugin.ts index 188a738d59794..f02b0b5e72999 100644 --- a/src/legacy/core_plugins/console/np_ready/public/plugin.ts +++ b/src/legacy/core_plugins/console/np_ready/public/plugin.ts @@ -18,26 +18,55 @@ */ import { render, unmountComponentAtNode } from 'react-dom'; +import { i18n } from '@kbn/i18n'; +import { FeatureCatalogueCategory } from 'ui/registry/feature_catalogue'; import { PluginInitializerContext, Plugin, CoreStart, CoreSetup } from '../../../../../core/public'; import { XPluginSet } from './legacy'; -import { boot } from './application'; export class ConsoleUIPlugin implements Plugin { // @ts-ignore constructor(private readonly ctx: PluginInitializerContext) {} - async setup({ application, notifications }: CoreSetup, pluginSet: XPluginSet) { + async setup({ notifications }: CoreSetup, pluginSet: XPluginSet) { const { - __LEGACY: { docLinkVersion, I18nContext, ResizeChecker }, + __LEGACY: { I18nContext, ResizeChecker }, + devTools, + feature_catalogue, } = pluginSet; - application.register({ + feature_catalogue.register({ + id: 'console', + title: i18n.translate('console.devToolsTitle', { + defaultMessage: 'Console', + }), + description: i18n.translate('console.devToolsDescription', { + defaultMessage: 'Skip cURL and use this JSON interface to work with your data directly.', + }), + icon: 'consoleApp', + path: '/app/kibana#/dev_tools/console', + showOnHomePage: true, + category: FeatureCatalogueCategory.ADMIN, + }); + + devTools.register({ id: 'console', order: 1, - title: 'Console', - mount(ctx, { element }) { - render(boot({ docLinkVersion, I18nContext, ResizeChecker, notifications }), element); + title: i18n.translate('console.consoleDisplayName', { + defaultMessage: 'Console', + }), + enableRouting: false, + async mount(ctx, { element }) { + const { boot } = await import('./application'); + render( + boot({ + docLinkVersion: ctx.core.docLinks.DOC_LINK_VERSION, + I18nContext, + ResizeChecker, + notifications, + }), + element + ); return () => { unmountComponentAtNode(element); }; diff --git a/src/legacy/core_plugins/console/public/quarantined/index.html b/src/legacy/core_plugins/console/public/quarantined/index.html deleted file mode 100644 index 66a693d4b2af7..0000000000000 --- a/src/legacy/core_plugins/console/public/quarantined/index.html +++ /dev/null @@ -1,3 +0,0 @@ - -
-
diff --git a/src/legacy/core_plugins/kibana/index.js b/src/legacy/core_plugins/kibana/index.js index 24cd436912395..c7cda8aec0165 100644 --- a/src/legacy/core_plugins/kibana/index.js +++ b/src/legacy/core_plugins/kibana/index.js @@ -62,7 +62,7 @@ export default function (kibana) { uiExports: { hacks: [ - 'plugins/kibana/dev_tools/hacks/hide_empty_tools', + 'plugins/kibana/dev_tools', ], fieldFormats: ['plugins/kibana/field_formats/register'], savedObjectTypes: [ diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/_index.scss b/src/legacy/core_plugins/kibana/public/dev_tools/_index.scss index 563b140fd2ead..2e88d2e1285e3 100644 --- a/src/legacy/core_plugins/kibana/public/dev_tools/_index.scss +++ b/src/legacy/core_plugins/kibana/public/dev_tools/_index.scss @@ -16,3 +16,6 @@ } } +.devApp { + height: 100%; +} diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/application.tsx b/src/legacy/core_plugins/kibana/public/dev_tools/application.tsx new file mode 100644 index 0000000000000..3945d8d8dc856 --- /dev/null +++ b/src/legacy/core_plugins/kibana/public/dev_tools/application.tsx @@ -0,0 +1,184 @@ +/* + * Licensed to Elasticsearch B.V. under one or more contributor + * license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright + * ownership. Elasticsearch B.V. licenses this file to you under + * the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import { I18nProvider } from '@kbn/i18n/react'; +import { i18n } from '@kbn/i18n'; +import { EuiTab, EuiTabs, EuiToolTip } from '@elastic/eui'; +import { HashRouter as Router, Switch, Route, Redirect } from 'react-router-dom'; +import * as React from 'react'; +import ReactDOM from 'react-dom'; +import { useEffect, useRef } from 'react'; + +import { AppMountContext } from 'kibana/public'; +import { DevTool } from '../../../../../plugins/dev_tools/public'; + +interface DevToolsWrapperProps { + devTools: readonly DevTool[]; + activeDevTool: DevTool; + appMountContext: AppMountContext; + updateRoute: (newRoute: string) => void; +} + +interface MountedDevToolDescriptor { + devTool: DevTool; + mountpoint: HTMLElement; + unmountHandler: () => void; +} + +function DevToolsWrapper({ + devTools, + activeDevTool, + appMountContext, + updateRoute, +}: DevToolsWrapperProps) { + const mountedTool = useRef(null); + + useEffect( + () => () => { + if (mountedTool.current) { + mountedTool.current.unmountHandler(); + } + }, + [] + ); + + return ( +
+ + {devTools.map(currentDevTool => ( + + { + if (!currentDevTool.disabled) { + updateRoute(`/dev_tools/${currentDevTool.id}`); + } + }} + > + {currentDevTool.title} + + + ))} + +
{ + if ( + element && + (mountedTool.current === null || + mountedTool.current.devTool !== activeDevTool || + mountedTool.current.mountpoint !== element) + ) { + if (mountedTool.current) { + mountedTool.current.unmountHandler(); + } + const unmountHandler = await activeDevTool.mount(appMountContext, { + element, + appBasePath: '', + }); + mountedTool.current = { + devTool: activeDevTool, + mountpoint: element, + unmountHandler, + }; + } + }} + /> +
+ ); +} + +function redirectOnMissingCapabilities(appMountContext: AppMountContext) { + if (!appMountContext.core.application.capabilities.dev_tools.show) { + window.location.hash = '/home'; + return true; + } + return false; +} + +function setBadge(appMountContext: AppMountContext) { + if (appMountContext.core.application.capabilities.dev_tools.save) { + return; + } + appMountContext.core.chrome.setBadge({ + text: i18n.translate('kbn.devTools.badge.readOnly.text', { + defaultMessage: 'Read only', + }), + tooltip: i18n.translate('kbn.devTools.badge.readOnly.tooltip', { + defaultMessage: 'Unable to save', + }), + iconType: 'glasses', + }); +} + +function setBreadcrumbs(appMountContext: AppMountContext) { + appMountContext.core.chrome.setBreadcrumbs([ + { + text: i18n.translate('kbn.devTools.k7BreadcrumbsDevToolsLabel', { + defaultMessage: 'Dev Tools', + }), + href: '#/dev_tools', + }, + ]); +} + +export function renderApp( + element: HTMLElement, + appMountContext: AppMountContext, + basePath: string, + devTools: readonly DevTool[] +) { + if (redirectOnMissingCapabilities(appMountContext)) { + return () => {}; + } + setBadge(appMountContext); + setBreadcrumbs(appMountContext); + ReactDOM.render( + + + + {devTools.map(devTool => ( + ( + + )} + /> + ))} + + + + + + , + element + ); + + return () => ReactDOM.unmountComponentAtNode(element); +} diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/directives/dev_tools_app.js b/src/legacy/core_plugins/kibana/public/dev_tools/directives/dev_tools_app.js deleted file mode 100644 index c7cb877be676b..0000000000000 --- a/src/legacy/core_plugins/kibana/public/dev_tools/directives/dev_tools_app.js +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import { uiModules } from 'ui/modules'; -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; -import template from '../partials/dev_tools_app.html'; - -uiModules - .get('apps/dev_tools') - .directive('kbnDevToolsApp', function (Private, $location) { - const devToolsRegistry = Private(DevToolsRegistryProvider); - - return { - restrict: 'E', - replace: true, - template, - transclude: true, - scope: { - topNavConfig: '=' - }, - bindToController: true, - controllerAs: 'kbnDevToolsApp', - controller() { - this.devTools = devToolsRegistry.inOrder; - this.currentPath = `#${$location.path()}`; - - this.onClick = (item, $event) => { - if (item.disabled) { - $event.preventDefault(); - } - }; - } - }; - }); diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/hacks/__tests__/hide_empty_tools.js b/src/legacy/core_plugins/kibana/public/dev_tools/hacks/__tests__/hide_empty_tools.js deleted file mode 100644 index 25c7b945b9dfb..0000000000000 --- a/src/legacy/core_plugins/kibana/public/dev_tools/hacks/__tests__/hide_empty_tools.js +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import expect from '@kbn/expect'; -import sinon from 'sinon'; - -import { hideEmptyDevTools } from '../hide_empty_tools'; -import { npStart } from 'ui/new_platform'; - -describe('hide dev tools', function () { - let updateNavLink; - - function PrivateWithoutTools() { - return []; - } - - function PrivateWithTools() { - return ['tool1', 'tool2']; - } - - function isHidden() { - return updateNavLink.calledWith('kibana:dev_tools', { hidden: true }); - } - - beforeEach(function () { - const coreNavLinks = npStart.core.chrome.navLinks; - updateNavLink = sinon.spy(coreNavLinks, 'update'); - }); - - it('should hide the app if there are no dev tools', function () { - hideEmptyDevTools(PrivateWithTools); - expect(isHidden()).to.be(false); - }); - - it('should not hide the app if there are tools', function () { - hideEmptyDevTools(PrivateWithoutTools); - expect(isHidden()).to.be(true); - }); - - afterEach(function () { - updateNavLink.restore(); - }); -}); diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/hacks/hide_empty_tools.js b/src/legacy/core_plugins/kibana/public/dev_tools/hacks/hide_empty_tools.js deleted file mode 100644 index 4dc55194562e5..0000000000000 --- a/src/legacy/core_plugins/kibana/public/dev_tools/hacks/hide_empty_tools.js +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import { uiModules } from 'ui/modules'; -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; -import { npStart } from 'ui/new_platform'; - -export function hideEmptyDevTools(Private) { - const hasTools = !!Private(DevToolsRegistryProvider).length; - if (!hasTools) { - npStart.core.chrome.navLinks.update('kibana:dev_tools', { - hidden: true - }); - } -} - -uiModules.get('kibana').run(hideEmptyDevTools); diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/index.js b/src/legacy/core_plugins/kibana/public/dev_tools/index.js deleted file mode 100644 index e36e75f6837ab..0000000000000 --- a/src/legacy/core_plugins/kibana/public/dev_tools/index.js +++ /dev/null @@ -1,77 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import uiRoutes from 'ui/routes'; -import { i18n } from '@kbn/i18n'; -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; -import { FeatureCatalogueRegistryProvider, FeatureCatalogueCategory } from 'ui/registry/feature_catalogue'; -import 'ui/directives/kbn_href'; -import './directives/dev_tools_app'; - -uiRoutes - .when('/dev_tools', { - resolve: { - redirect(Private, kbnUrl) { - const items = Private(DevToolsRegistryProvider).inOrder; - kbnUrl.redirect(items[0].url.substring(1)); - } - } - }); - -uiRoutes.defaults(/^\/dev_tools(\/|$)/, { - badge: uiCapabilities => { - if (uiCapabilities.dev_tools.save) { - return undefined; - } - - return { - text: i18n.translate('kbn.devTools.badge.readOnly.text', { - defaultMessage: 'Read only', - }), - tooltip: i18n.translate('kbn.devTools.badge.readOnly.tooltip', { - defaultMessage: 'Unable to save', - }), - iconType: 'glasses' - }; - }, - k7Breadcrumbs: () => [ - { - text: i18n.translate('kbn.devTools.k7BreadcrumbsDevToolsLabel', { - defaultMessage: 'Dev Tools' - }), - href: '#/dev_tools' - } - ] -}); - -FeatureCatalogueRegistryProvider.register(() => { - return { - id: 'console', - title: i18n.translate('kbn.devTools.consoleTitle', { - defaultMessage: 'Console' - }), - description: i18n.translate('kbn.devTools.consoleDescription', { - defaultMessage: 'Skip cURL and use this JSON interface to work with your data directly.' - }), - icon: 'consoleApp', - path: '/app/kibana#/dev_tools/console', - showOnHomePage: true, - category: FeatureCatalogueCategory.ADMIN - }; -}); diff --git a/src/legacy/core_plugins/console/public/quarantined/hacks/register.js b/src/legacy/core_plugins/kibana/public/dev_tools/index.ts similarity index 68% rename from src/legacy/core_plugins/console/public/quarantined/hacks/register.js rename to src/legacy/core_plugins/kibana/public/dev_tools/index.ts index b5df1c1af99c5..74708e36a98aa 100644 --- a/src/legacy/core_plugins/console/public/quarantined/hacks/register.js +++ b/src/legacy/core_plugins/kibana/public/dev_tools/index.ts @@ -17,14 +17,18 @@ * under the License. */ -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; -import { i18n } from '@kbn/i18n'; +import { npSetup, npStart } from 'ui/new_platform'; -DevToolsRegistryProvider.register(() => ({ - order: 1, - name: 'console', - display: i18n.translate('console.consoleDisplayName', { - defaultMessage: 'Console', - }), - url: '#/dev_tools/console', -})); +import { DevToolsPlugin } from './plugin'; +import { localApplicationService } from '../local_application_service'; + +const instance = new DevToolsPlugin(); + +instance.setup(npSetup.core, { + __LEGACY: { + localApplicationService, + }, +}); +instance.start(npStart.core, { + newPlatformDevTools: npStart.plugins.devTools, +}); diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/partials/dev_tools_app.html b/src/legacy/core_plugins/kibana/public/dev_tools/partials/dev_tools_app.html deleted file mode 100644 index 6c076092c76d5..0000000000000 --- a/src/legacy/core_plugins/kibana/public/dev_tools/partials/dev_tools_app.html +++ /dev/null @@ -1,22 +0,0 @@ -
- - -
-
diff --git a/src/legacy/core_plugins/kibana/public/dev_tools/plugin.ts b/src/legacy/core_plugins/kibana/public/dev_tools/plugin.ts new file mode 100644 index 0000000000000..ec9af1a6acd92 --- /dev/null +++ b/src/legacy/core_plugins/kibana/public/dev_tools/plugin.ts @@ -0,0 +1,71 @@ +/* + * Licensed to Elasticsearch B.V. under one or more contributor + * license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright + * ownership. Elasticsearch B.V. licenses this file to you under + * the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +// This import makes sure dev tools are registered before the app is. +import 'uiExports/devTools'; + +import { CoreSetup, CoreStart, Plugin } from 'kibana/public'; + +import { LocalApplicationService } from '../local_application_service'; +import { DevTool, DevToolsStart } from '../../../../../plugins/dev_tools/public'; + +export interface DevToolsPluginSetupDependencies { + __LEGACY: { + localApplicationService: LocalApplicationService; + }; +} + +export interface DevToolsPluginStartDependencies { + newPlatformDevTools: DevToolsStart; +} + +export class DevToolsPlugin implements Plugin { + private getSortedDevTools: (() => readonly DevTool[]) | null = null; + + public setup( + core: CoreSetup, + { __LEGACY: { localApplicationService } }: DevToolsPluginSetupDependencies + ) { + localApplicationService.register({ + id: 'dev_tools', + title: 'Dev Tools', + mount: async (appMountContext, params) => { + if (!this.getSortedDevTools) { + throw new Error('not started yet'); + } + const { renderApp } = await import('./application'); + return renderApp( + params.element, + appMountContext, + params.appBasePath, + this.getSortedDevTools() + ); + }, + }); + } + + public start(core: CoreStart, { newPlatformDevTools }: DevToolsPluginStartDependencies) { + this.getSortedDevTools = newPlatformDevTools.getSortedDevTools; + if (this.getSortedDevTools().length === 0) { + core.chrome.navLinks.update('kibana:dev_tools', { + hidden: true, + }); + } + } +} diff --git a/src/legacy/core_plugins/kibana/public/kibana.js b/src/legacy/core_plugins/kibana/public/kibana.js index fe741a357cbfe..c5b9d86b57aae 100644 --- a/src/legacy/core_plugins/kibana/public/kibana.js +++ b/src/legacy/core_plugins/kibana/public/kibana.js @@ -37,7 +37,6 @@ import 'uiExports/navbarExtensions'; import 'uiExports/contextMenuActions'; import 'uiExports/managementSections'; import 'uiExports/indexManagement'; -import 'uiExports/devTools'; import 'uiExports/docViews'; import 'uiExports/embeddableFactories'; import 'uiExports/embeddableActions'; diff --git a/src/legacy/plugin_discovery/types.ts b/src/legacy/plugin_discovery/types.ts index c14daa37f5706..dfd36f2aa7b2b 100644 --- a/src/legacy/plugin_discovery/types.ts +++ b/src/legacy/plugin_discovery/types.ts @@ -62,7 +62,6 @@ export interface LegacyPluginOptions { }>; apps: any; hacks: string[]; - devTools: string[]; styleSheetPaths: string; injectDefaultVars: (server: Server) => Record; noParse: string[]; diff --git a/src/legacy/ui/public/new_platform/new_platform.karma_mock.js b/src/legacy/ui/public/new_platform/new_platform.karma_mock.js index bb055d6ce1e33..e62ceeb2f3102 100644 --- a/src/legacy/ui/public/new_platform/new_platform.karma_mock.js +++ b/src/legacy/ui/public/new_platform/new_platform.karma_mock.js @@ -62,6 +62,9 @@ export const npSetup = { } }, }, + devTools: { + register: () => {}, + }, inspector: { registerView: () => undefined, __LEGACY: { @@ -97,6 +100,9 @@ export const npStart = { registerRenderer: sinon.fake(), registerType: sinon.fake(), }, + devTools: { + getSortedDevTools: () => [], + }, data: { autocomplete: { getProvider: sinon.fake(), diff --git a/src/legacy/ui/public/new_platform/new_platform.ts b/src/legacy/ui/public/new_platform/new_platform.ts index 0c7b28e7da3df..9ee5d8580a90b 100644 --- a/src/legacy/ui/public/new_platform/new_platform.ts +++ b/src/legacy/ui/public/new_platform/new_platform.ts @@ -28,6 +28,7 @@ import { Start as InspectorStart, } from '../../../../plugins/inspector/public'; import { EuiUtilsStart } from '../../../../plugins/eui_utils/public'; +import { DevToolsSetup, DevToolsStart } from '../../../../plugins/dev_tools/public'; import { FeatureCatalogueSetup, FeatureCatalogueStart, @@ -40,6 +41,7 @@ export interface PluginsSetup { feature_catalogue: FeatureCatalogueSetup; inspector: InspectorSetup; uiActions: IUiActionsSetup; + devTools: DevToolsSetup; } export interface PluginsStart { @@ -50,6 +52,7 @@ export interface PluginsStart { feature_catalogue: FeatureCatalogueStart; inspector: InspectorStart; uiActions: IUiActionsStart; + devTools: DevToolsStart; } export const npSetup = { diff --git a/src/plugins/dev_tools/README.md b/src/plugins/dev_tools/README.md new file mode 100644 index 0000000000000..1610411b9c98e --- /dev/null +++ b/src/plugins/dev_tools/README.md @@ -0,0 +1,29 @@ +# Dev tools plugin + +The ui/registry/dev_tools is removed in favor of the `dev_tools` plugin which exposes a register method in the setup contract. +Registering app works mostly the same as registering apps in core.application.register. +Routing will be handled by the id of the dev tool - your dev tool will be mounted when the URL matches `/app/kibana#/dev_tools/`. +This API doesn't support angular, for registering angular dev tools, bootstrap a local module on mount into the given HTML element. + +During the migration this plugin exposes the registered dev tools in the start contract. This is necessary to keep the dev tools app +which is still living in the legacy platform working and will be removed once everything is moved over to the new platform. It should +not be used by other plugins. + +## Example registration + +```ts +// For legacy plugins +import { npSetup } from 'ui/new_platform'; +npSetup.plugins.dev_tools.register(/* same details here */); + +// For new plugins: first add 'dev_tools' to the list of `optionalPlugins` +// in your kibana.json file. Then access the plugin directly in `setup`: + +class MyPlugin { + setup(core, plugins) { + if (plugins.dev_tools) { + plugins.dev_tools.register(/* same details here. */); + } + } +} +``` diff --git a/src/plugins/dev_tools/kibana.json b/src/plugins/dev_tools/kibana.json new file mode 100644 index 0000000000000..307035c7ec664 --- /dev/null +++ b/src/plugins/dev_tools/kibana.json @@ -0,0 +1,6 @@ +{ + "id": "devTools", + "version": "kibana", + "server": false, + "ui": true +} diff --git a/src/legacy/ui/public/registry/dev_tools.js b/src/plugins/dev_tools/public/index.ts similarity index 77% rename from src/legacy/ui/public/registry/dev_tools.js rename to src/plugins/dev_tools/public/index.ts index 1741f39f86375..3a0d1455e2168 100644 --- a/src/legacy/ui/public/registry/dev_tools.js +++ b/src/plugins/dev_tools/public/index.ts @@ -17,11 +17,11 @@ * under the License. */ -import { uiRegistry } from './_registry'; +import { PluginInitializerContext } from 'kibana/public'; +import { DevToolsPlugin } from './plugin'; -export const DevToolsRegistryProvider = uiRegistry({ - name: 'devTools', - index: ['name'], - order: ['order'] -}); +export function plugin(initializerContext: PluginInitializerContext) { + return new DevToolsPlugin(); +} +export * from './plugin'; diff --git a/src/plugins/dev_tools/public/plugin.ts b/src/plugins/dev_tools/public/plugin.ts new file mode 100644 index 0000000000000..8098308c0882b --- /dev/null +++ b/src/plugins/dev_tools/public/plugin.ts @@ -0,0 +1,115 @@ +/* + * Licensed to Elasticsearch B.V. under one or more contributor + * license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright + * ownership. Elasticsearch B.V. licenses this file to you under + * the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import { App, CoreSetup, Plugin } from 'kibana/public'; +import { sortBy } from 'lodash'; + +export interface DevToolsSetup { + /** + * Register a developer tool. It will be available + * in the dev tools app under a separate tab. + * + * Registering dev tools works almost similar to registering + * applications in the core application service, + * but they will be rendered with a frame containing tabs + * to switch between the tools. + * @param devTool The dev tools descriptor + */ + register: (devTool: DevTool) => void; +} + +export interface DevToolsStart { + /** + * Returns all registered dev tools in an ordered array. + * This function is only exposed because the dev tools app + * actually rendering the tool has to stay in the legacy platform + * for now. Once it is moved into this plugin, this function + * becomes an implementation detail. + * @deprecated + */ + getSortedDevTools: () => readonly DevTool[]; +} + +/** + * Descriptor for a dev tool. A dev tool works similar to an application + * registered in the core application service. + */ +export interface DevTool { + /** + * The id of the dev tools. This will become part of the URL path + * (`dev_tools/${devTool.id}`. It has to be unique among registered + * dev tools. + */ + id: string; + /** + * The human readable name of the dev tool. Should be internationalized. + * This will be used as a label in the tab above the actual tool. + */ + title: string; + mount: App['mount']; + /** + * Flag indicating to disable the tab of this dev tool. Navigating to a + * disabled dev tool will be treated as the navigation to an unknown route + * (redirect to the console). + */ + disabled?: boolean; + /** + * Optional tooltip content of the tab. + */ + tooltipContent?: string; + /** + * Flag indicating whether the dev tool will do routing within the `dev_tools/${devTool.id}/` + * prefix. If it is set to true, the dev tool is responsible to redirect + * the user when navigating to unknown URLs within the prefix. If set + * to false only the root URL of the dev tool will be recognized as valid. + */ + enableRouting: boolean; + /** + * Number used to order the tabs. + */ + order: number; +} + +export class DevToolsPlugin implements Plugin { + private readonly devTools = new Map(); + + private getSortedDevTools(): readonly DevTool[] { + return sortBy([...this.devTools.values()], 'order'); + } + + public setup(core: CoreSetup) { + return { + register: (devTool: DevTool) => { + if (this.devTools.has(devTool.id)) { + throw new Error( + `Dev tool with id [${devTool.id}] has already been registered. Use a unique id.` + ); + } + + this.devTools.set(devTool.id, devTool); + }, + }; + } + + public start() { + return { + getSortedDevTools: this.getSortedDevTools.bind(this), + }; + } +} diff --git a/x-pack/legacy/plugins/grokdebugger/index.js b/x-pack/legacy/plugins/grokdebugger/index.js index 337e913bb3e6f..8dd0945743bf0 100644 --- a/x-pack/legacy/plugins/grokdebugger/index.js +++ b/x-pack/legacy/plugins/grokdebugger/index.js @@ -20,8 +20,7 @@ export const grokdebugger = (kibana) => new kibana.Plugin({ }).default(); }, uiExports: { - devTools: ['plugins/grokdebugger/sections/grokdebugger'], - hacks: ['plugins/grokdebugger/sections/grokdebugger/register'], + devTools: ['plugins/grokdebugger/register'], home: ['plugins/grokdebugger/register_feature'], }, init: (server) => { diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/custom_patterns_input/custom_patterns_input.js b/x-pack/legacy/plugins/grokdebugger/public/components/custom_patterns_input/custom_patterns_input.js similarity index 96% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/custom_patterns_input/custom_patterns_input.js rename to x-pack/legacy/plugins/grokdebugger/public/components/custom_patterns_input/custom_patterns_input.js index 87df1976b7dc8..cc1d2bc53a9df 100644 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/custom_patterns_input/custom_patterns_input.js +++ b/x-pack/legacy/plugins/grokdebugger/public/components/custom_patterns_input/custom_patterns_input.js @@ -14,7 +14,7 @@ import { EuiCodeEditor, EuiSpacer } from '@elastic/eui'; -import { EDITOR } from '../../../../../common/constants'; +import { EDITOR } from '../../../common/constants'; import { FormattedMessage } from '@kbn/i18n/react'; export function CustomPatternsInput({ value, onChange }) { diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/custom_patterns_input/index.js b/x-pack/legacy/plugins/grokdebugger/public/components/custom_patterns_input/index.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/custom_patterns_input/index.js rename to x-pack/legacy/plugins/grokdebugger/public/components/custom_patterns_input/index.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_input/event_input.js b/x-pack/legacy/plugins/grokdebugger/public/components/event_input/event_input.js similarity index 94% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_input/event_input.js rename to x-pack/legacy/plugins/grokdebugger/public/components/event_input/event_input.js index 00ee2dbd9074c..19335a88e9b87 100644 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_input/event_input.js +++ b/x-pack/legacy/plugins/grokdebugger/public/components/event_input/event_input.js @@ -10,7 +10,7 @@ import { EuiPanel, EuiCodeEditor } from '@elastic/eui'; -import { EDITOR } from '../../../../../common/constants'; +import { EDITOR } from '../../../common/constants'; import { FormattedMessage } from '@kbn/i18n/react'; export function EventInput({ value, onChange }) { diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_input/index.js b/x-pack/legacy/plugins/grokdebugger/public/components/event_input/index.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_input/index.js rename to x-pack/legacy/plugins/grokdebugger/public/components/event_input/index.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_output/event_output.js b/x-pack/legacy/plugins/grokdebugger/public/components/event_output/event_output.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_output/event_output.js rename to x-pack/legacy/plugins/grokdebugger/public/components/event_output/event_output.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_output/index.js b/x-pack/legacy/plugins/grokdebugger/public/components/event_output/index.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/event_output/index.js rename to x-pack/legacy/plugins/grokdebugger/public/components/event_output/index.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/grok_debugger/grok_debugger.js b/x-pack/legacy/plugins/grokdebugger/public/components/grok_debugger/grok_debugger.js similarity index 98% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/grok_debugger/grok_debugger.js rename to x-pack/legacy/plugins/grokdebugger/public/components/grok_debugger/grok_debugger.js index eaf66b2b1a044..2a9fa499f37ea 100644 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/grok_debugger/grok_debugger.js +++ b/x-pack/legacy/plugins/grokdebugger/public/components/grok_debugger/grok_debugger.js @@ -18,7 +18,7 @@ import { EventInput } from '../event_input'; import { PatternInput } from '../pattern_input'; import { CustomPatternsInput } from '../custom_patterns_input'; import { EventOutput } from '../event_output'; -import { GrokdebuggerRequest } from '../../../../models/grokdebugger_request'; +import { GrokdebuggerRequest } from '../../models/grokdebugger_request'; import { toastNotifications } from 'ui/notify'; import { FormattedMessage } from '@kbn/i18n/react'; diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/grok_debugger/index.js b/x-pack/legacy/plugins/grokdebugger/public/components/grok_debugger/index.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/grok_debugger/index.js rename to x-pack/legacy/plugins/grokdebugger/public/components/grok_debugger/index.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/pattern_input/index.js b/x-pack/legacy/plugins/grokdebugger/public/components/pattern_input/index.js similarity index 100% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/pattern_input/index.js rename to x-pack/legacy/plugins/grokdebugger/public/components/pattern_input/index.js diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/pattern_input/pattern_input.js b/x-pack/legacy/plugins/grokdebugger/public/components/pattern_input/pattern_input.js similarity index 91% rename from x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/pattern_input/pattern_input.js rename to x-pack/legacy/plugins/grokdebugger/public/components/pattern_input/pattern_input.js index bb06da7183b9a..09a6e100d9f88 100644 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/components/pattern_input/pattern_input.js +++ b/x-pack/legacy/plugins/grokdebugger/public/components/pattern_input/pattern_input.js @@ -10,8 +10,8 @@ import { EuiPanel, EuiCodeEditor } from '@elastic/eui'; -import { EDITOR } from '../../../../../common/constants'; -import { GrokMode } from '../../../../lib/ace'; +import { EDITOR } from '../../../common/constants'; +import { GrokMode } from '../../lib/ace'; import { FormattedMessage } from '@kbn/i18n/react'; export function PatternInput({ value, onChange }) { diff --git a/x-pack/legacy/plugins/grokdebugger/public/register.js b/x-pack/legacy/plugins/grokdebugger/public/register.js new file mode 100644 index 0000000000000..74679d65e52d2 --- /dev/null +++ b/x-pack/legacy/plugins/grokdebugger/public/register.js @@ -0,0 +1,33 @@ +/* + * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one + * or more contributor license agreements. Licensed under the Elastic License; + * you may not use this file except in compliance with the Elastic License. + */ + +import { i18n } from '@kbn/i18n'; +import { xpackInfo } from 'plugins/xpack_main/services/xpack_info'; +import { npSetup, npStart } from 'ui/new_platform'; + +npSetup.plugins.devTools.register({ + order: 6, + title: i18n.translate('xpack.grokDebugger.displayName', { + defaultMessage: 'Grok Debugger', + }), + id: 'grokdebugger', + enableRouting: false, + disabled: !xpackInfo.get('features.grokdebugger.enableLink', false), + tooltipContent: xpackInfo.get('features.grokdebugger.message'), + async mount(context, { element }) { + const licenseCheck = { + showPage: xpackInfo.get('features.grokdebugger.enableLink'), + message: xpackInfo.get('features.grokdebugger.message'), + }; + if (!licenseCheck.showPage) { + npStart.core.notifications.toasts.addDanger(licenseCheck.message); + window.location.hash = '/dev_tools'; + return () => {}; + } + const { renderApp } = await import('./render_app'); + return renderApp(element, npStart); + }, +}); diff --git a/x-pack/legacy/plugins/grokdebugger/public/render_app.js b/x-pack/legacy/plugins/grokdebugger/public/render_app.js new file mode 100644 index 0000000000000..2c4894bb70ee1 --- /dev/null +++ b/x-pack/legacy/plugins/grokdebugger/public/render_app.js @@ -0,0 +1,22 @@ +/* + * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one + * or more contributor license agreements. Licensed under the Elastic License; + * you may not use this file except in compliance with the Elastic License. + */ + +import React from 'react'; +import { render, unmountComponentAtNode } from 'react-dom'; + +import { GrokDebugger } from './components/grok_debugger'; +import { GrokdebuggerService } from './services/grokdebugger/grokdebugger_service'; +import { I18nProvider } from '@kbn/i18n/react'; + +export function renderApp(element, npStart) { + render( + + + , + element + ); + return () => unmountComponentAtNode(element); +} diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/grokdebugger.js b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/grokdebugger.js deleted file mode 100644 index a07ba56057b4b..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/grokdebugger.js +++ /dev/null @@ -1,25 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import { uiModules } from 'ui/modules'; -import 'plugins/grokdebugger/services/grokdebugger'; -import { GrokDebugger } from '../../components/grok_debugger'; -import { render } from 'react-dom'; -import React from 'react'; -import { I18nContext } from 'ui/i18n'; - -const app = uiModules.get('xpack/grokdebugger'); - -app.directive('grokdebugger', function ($injector) { - const grokdebuggerService = $injector.get('grokdebuggerService'); - - return { - restrict: 'E', - link: (scope, el) => { - render(, el[0]); - } - }; -}); diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/index.js b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/index.js deleted file mode 100644 index b33973ed71736..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/directives/grokdebugger/index.js +++ /dev/null @@ -1,7 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import './grokdebugger'; diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.html b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.html deleted file mode 100644 index f1de4653ead0a..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.html +++ /dev/null @@ -1,3 +0,0 @@ - - - diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.js b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.js deleted file mode 100644 index 9f588bbe510ae..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/grokdebugger_route.js +++ /dev/null @@ -1,40 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import routes from 'ui/routes'; -import 'ui/capabilities/route_setup'; -import { toastNotifications } from 'ui/notify'; -import { xpackInfo } from 'plugins/xpack_main/services/xpack_info'; -import template from './grokdebugger_route.html'; -import './directives/grokdebugger'; - - -routes - .when('/dev_tools/grokdebugger', { - template: template, - requireUICapability: 'dev_tools.show', - resolve: { - licenseCheckResults() { - return { - showPage: xpackInfo.get('features.grokdebugger.enableLink'), - message: xpackInfo.get('features.grokdebugger.message') - }; - } - }, - controller: class GrokDebuggerRouteController { - constructor($injector) { - const $route = $injector.get('$route'); - const kbnUrl = $injector.get('kbnUrl'); - - const licenseCheckResults = $route.current.locals.licenseCheckResults; - if (!licenseCheckResults.showPage) { - kbnUrl.change('/dev_tools'); - toastNotifications.addDanger(licenseCheckResults.message); - return; - } - } - } - }); diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/index.js b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/index.js deleted file mode 100644 index b9fb58f1f12c9..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/index.js +++ /dev/null @@ -1,7 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import './grokdebugger_route'; diff --git a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/register.js b/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/register.js deleted file mode 100644 index 0a2ea2644bf14..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/sections/grokdebugger/register.js +++ /dev/null @@ -1,22 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; -import { i18n } from '@kbn/i18n'; -import { xpackInfo } from 'plugins/xpack_main/services/xpack_info'; - -DevToolsRegistryProvider.register(() => { - return { - order: 6, - name: 'grokdebugger', - display: i18n.translate('xpack.grokDebugger.displayName', { - defaultMessage: 'Grok Debugger', - }), - url: '#/dev_tools/grokdebugger', - disabled: !xpackInfo.get('features.grokdebugger.enableLink', false), - tooltipContent: xpackInfo.get('features.grokdebugger.message') - }; -}); diff --git a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.factory.js b/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.factory.js deleted file mode 100644 index 17dc66d67e872..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.factory.js +++ /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; - * you may not use this file except in compliance with the Elastic License. - */ - -import { uiModules } from 'ui/modules'; -import { GrokdebuggerService } from './grokdebugger_service'; - -uiModules.get('xpack/grokdebugger') - .factory('grokdebuggerService', ($injector) => { - const $http = $injector.get('$http'); - return new GrokdebuggerService($http); - }); diff --git a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.js b/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.js index 56041949c1ff8..7a656b33d59ff 100644 --- a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.js +++ b/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/grokdebugger_service.js @@ -9,18 +9,19 @@ import { ROUTES } from '../../../common/constants'; import { GrokdebuggerResponse } from 'plugins/grokdebugger/models/grokdebugger_response'; export class GrokdebuggerService { - constructor($http) { - this.$http = $http; + constructor(http) { + this.http = http; this.basePath = chrome.addBasePath(ROUTES.API_ROOT); } simulate(grokdebuggerRequest) { - return this.$http.post(`${this.basePath}/simulate`, grokdebuggerRequest.upstreamJSON) + return this.http + .post(`${this.basePath}/simulate`, { body: JSON.stringify(grokdebuggerRequest.upstreamJSON) }) .then(response => { - return GrokdebuggerResponse.fromUpstreamJSON(response.data.grokdebuggerResponse); + return GrokdebuggerResponse.fromUpstreamJSON(response.grokdebuggerResponse); }) .catch(e => { - throw e.data.message; + throw e.body.message; }); } } diff --git a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/index.js b/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/index.js deleted file mode 100644 index 766ed7c8766ae..0000000000000 --- a/x-pack/legacy/plugins/grokdebugger/public/services/grokdebugger/index.js +++ /dev/null @@ -1,7 +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; - * you may not use this file except in compliance with the Elastic License. - */ - -import './grokdebugger_service.factory'; diff --git a/x-pack/legacy/plugins/searchprofiler/index.ts b/x-pack/legacy/plugins/searchprofiler/index.ts index 5de6ba710235b..834f331cd7bf4 100644 --- a/x-pack/legacy/plugins/searchprofiler/index.ts +++ b/x-pack/legacy/plugins/searchprofiler/index.ts @@ -26,7 +26,6 @@ export const searchprofiler = (kibana: any) => { devTools: [`${publicSrc}/legacy`], styleSheetPaths: `${publicSrc}/np_ready/application/index.scss`, // Legacy - hacks: ['plugins/searchprofiler/register'], home: ['plugins/searchprofiler/register_feature'], }, init(server: Server) { diff --git a/x-pack/legacy/plugins/searchprofiler/public/legacy.ts b/x-pack/legacy/plugins/searchprofiler/public/legacy.ts index 61dabe8ac7b05..b767705e025a0 100644 --- a/x-pack/legacy/plugins/searchprofiler/public/legacy.ts +++ b/x-pack/legacy/plugins/searchprofiler/public/legacy.ts @@ -7,59 +7,22 @@ /* eslint-disable @kbn/eslint/no-restricted-paths */ import { npSetup } from 'ui/new_platform'; import { I18nContext } from 'ui/i18n'; -import uiRoutes from 'ui/routes'; -import 'ui/capabilities/route_setup'; // @ts-ignore import { xpackInfo } from 'plugins/xpack_main/services/xpack_info'; // @ts-ignore import { formatAngularHttpError } from 'ui/notify/lib'; import 'ui/autoload/all'; -/* eslint-enable @kbn/eslint/no-restricted-paths */ -import { ApplicationSetup } from 'src/core/public'; import { plugin } from './np_ready'; const pluginInstance = plugin({} as any); -const template = ` -
-`; - -uiRoutes.when('/dev_tools/searchprofiler', { - template, - requireUICapability: 'dev_tools.show', - controller: $scope => { - $scope.startReactApp = () => { - const el = document.querySelector('#searchProfilerAppRoot'); - if (!el) { - const errorMessage = 'Could not mount Searchprofiler App!'; - npSetup.core.fatalErrors.add(errorMessage); - throw new Error(errorMessage); - } - - const coreApplicationSetupShim: ApplicationSetup = { - register(app: any) { - const unmount = app.mount(); - $scope.$on('$destroy', () => unmount()); - }, - registerMountContext: {} as any, - }; - - pluginInstance.setup( - { - ...npSetup.core, - application: coreApplicationSetupShim, - }, - { - __LEGACY: { - I18nContext, - licenseEnabled: xpackInfo.get('features.searchprofiler.enableAppLink'), - notifications: npSetup.core.notifications.toasts, - formatAngularHttpError, - el, - }, - } - ); - }; +pluginInstance.setup(npSetup.core, { + ...npSetup.plugins, + __LEGACY: { + I18nContext, + licenseEnabled: xpackInfo.get('features.searchprofiler.enableAppLink'), + notifications: npSetup.core.notifications.toasts, + formatAngularHttpError, }, }); diff --git a/x-pack/legacy/plugins/searchprofiler/public/np_ready/plugin.ts b/x-pack/legacy/plugins/searchprofiler/public/np_ready/plugin.ts index ff98e706abf5c..7a5981fcb0a69 100644 --- a/x-pack/legacy/plugins/searchprofiler/public/np_ready/plugin.ts +++ b/x-pack/legacy/plugins/searchprofiler/public/np_ready/plugin.ts @@ -4,6 +4,7 @@ * you may not use this file except in compliance with the Elastic License. */ +import { i18n } from '@kbn/i18n'; import { Plugin, CoreStart, @@ -12,7 +13,7 @@ import { ToastsStart, } from 'src/core/public'; -import { boot } from './application/boot'; +import { DevToolsSetup } from '../../../../../../src/plugins/dev_tools/public'; export class SearchProfilerUIPlugin implements Plugin { constructor(ctx: PluginInitializerContext) {} @@ -25,22 +26,28 @@ export class SearchProfilerUIPlugin implements Plugin { licenseEnabled: boolean; notifications: ToastsStart; formatAngularHttpError: any; - el: HTMLElement; }; + devTools: DevToolsSetup; } ) { const { http } = core; const { - __LEGACY: { I18nContext, licenseEnabled, notifications, formatAngularHttpError, el }, + __LEGACY: { I18nContext, licenseEnabled, notifications, formatAngularHttpError }, + devTools, } = plugins; - core.application.register({ + devTools.register({ id: 'searchprofiler', - title: 'SearchProfiler', - mount(ctx, params) { + title: i18n.translate('xpack.searchProfiler.pageDisplayName', { + defaultMessage: 'Search Profiler', + }), + order: 5, + enableRouting: false, + async mount(ctx, params) { + const { boot } = await import('./application/boot'); return boot({ http, licenseEnabled, - el, + el: params.element, I18nContext, notifications, formatAngularHttpError, diff --git a/x-pack/legacy/plugins/searchprofiler/public/register.js b/x-pack/legacy/plugins/searchprofiler/public/register.js deleted file mode 100644 index 45da747801a4b..0000000000000 --- a/x-pack/legacy/plugins/searchprofiler/public/register.js +++ /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; - * you may not use this file except in compliance with the Elastic License. - */ - -import { DevToolsRegistryProvider } from 'ui/registry/dev_tools'; - -import { i18n } from '@kbn/i18n'; - -DevToolsRegistryProvider.register(() => ({ - order: 5, - name: 'searchprofiler', - - display: i18n.translate('xpack.searchProfiler.pageDisplayName', { - defaultMessage: 'Search Profiler', - }), - - url: '#/dev_tools/searchprofiler' -})); diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index f745c7b40d703..34491036e5a45 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -712,6 +712,8 @@ "inspector.requests.statisticsTabLabel": "統計", "console.autocomplete.addMethodMetaText": "メソド", "console.consoleDisplayName": "コンソール", + "console.devToolsDescription": "cURL をスキップしこの JSON インスタンスを使って、データに直接アクセスします。", + "console.devToolsTitle": "コンソール", "console.helpPage.keyboardCommands.autoIndentDescription": "現在のリクエストを自動インデントします", "console.helpPage.keyboardCommands.closeAutoCompleteMenuDescription": "自動入力メニューを閉じます", "console.helpPage.keyboardCommands.collapseAllScopesDescription": "現在のスコープを除きすべてのスコープを最小表示します。シフトを追加して拡張します。", @@ -1490,8 +1492,6 @@ "kbn.dashboardTitle": "ダッシュボード", "kbn.devTools.badge.readOnly.text": "読み込み専用", "kbn.devTools.badge.readOnly.tooltip": "を保存できませんでした", - "kbn.devTools.consoleDescription": "cURL をスキップしこの JSON インスタンスを使って、データに直接アクセスします。", - "kbn.devTools.consoleTitle": "コンソール", "kbn.devTools.k7BreadcrumbsDevToolsLabel": "開発ツール", "kbn.devToolsTitle": "開発ツール", "kbn.discover.backToTopLinkText": "最上部へ戻る。", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index 52b45200b7ff7..df00be9685ccf 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -713,6 +713,8 @@ "inspector.requests.statisticsTabLabel": "统计信息", "console.autocomplete.addMethodMetaText": "方法", "console.consoleDisplayName": "Console", + "console.devToolsDescription": "跳过 cURL 并使用此 JSON 接口来直接处理您的数据。", + "console.devToolsTitle": "Console", "console.helpPage.keyboardCommands.autoIndentDescription": "自动缩进当前请求", "console.helpPage.keyboardCommands.closeAutoCompleteMenuDescription": "关闭自动完成菜单", "console.helpPage.keyboardCommands.collapseAllScopesDescription": "折叠当前范围除外的所有范围。通过加按 Shift 键来展开。", @@ -1491,8 +1493,6 @@ "kbn.dashboardTitle": "仪表板", "kbn.devTools.badge.readOnly.text": "只读", "kbn.devTools.badge.readOnly.tooltip": "无法保存", - "kbn.devTools.consoleDescription": "跳过 cURL 并使用此 JSON 接口来直接处理您的数据。", - "kbn.devTools.consoleTitle": "Console", "kbn.devTools.k7BreadcrumbsDevToolsLabel": "开发工具", "kbn.devToolsTitle": "开发工具", "kbn.discover.backToTopLinkText": "返至顶部。", diff --git a/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_security.ts b/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_security.ts index 1a63a6ad3c9e4..95bcdb195e09e 100644 --- a/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_security.ts +++ b/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_security.ts @@ -90,7 +90,7 @@ export default function({ getPageObjects, getService }: FtrProviderContext) { }); it(`can navigate to search profiler`, async () => { - await testSubjects.existOrFail('searchProfiler'); + await testSubjects.existOrFail('searchprofiler'); }); it(`doesn't show read-only badge`, async () => { @@ -173,7 +173,7 @@ export default function({ getPageObjects, getService }: FtrProviderContext) { }); it(`can navigate to search profiler`, async () => { - await testSubjects.existOrFail('searchProfiler'); + await testSubjects.existOrFail('searchprofiler'); }); it(`shows read-only badge`, async () => { diff --git a/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_spaces.ts b/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_spaces.ts index 666b9175da275..1c052e0103e70 100644 --- a/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_spaces.ts +++ b/x-pack/test/functional/apps/dev_tools/feature_controls/dev_tools_spaces.ts @@ -54,7 +54,7 @@ export default function({ getPageObjects, getService }: FtrProviderContext) { it(`can navigate to search profiler`, async () => { await PageObjects.common.navigateToApp('searchProfiler'); - await testSubjects.existOrFail('searchProfiler'); + await testSubjects.existOrFail('searchprofiler'); }); it(`can navigate to grok debugger`, async () => { From cbc1c7d52f97f10d109d1bacd56ba2af42bb3352 Mon Sep 17 00:00:00 2001 From: MadameSheema Date: Thu, 14 Nov 2019 10:51:25 +0100 Subject: [PATCH 3/9] fixes inspect tests (#50510) --- .../siem/cypress/integration/lib/inspect/selectors.ts | 6 +++--- .../plugins/siem/cypress/integration/lib/urls/index.ts | 3 +++ 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/x-pack/legacy/plugins/siem/cypress/integration/lib/inspect/selectors.ts b/x-pack/legacy/plugins/siem/cypress/integration/lib/inspect/selectors.ts index dc998c0764acf..689c98de9598a 100644 --- a/x-pack/legacy/plugins/siem/cypress/integration/lib/inspect/selectors.ts +++ b/x-pack/legacy/plugins/siem/cypress/integration/lib/inspect/selectors.ts @@ -4,7 +4,7 @@ * you may not use this file except in compliance with the Elastic License. */ -import { HOSTS_PAGE, HOSTS_PAGE_TAB_URLS, NETWORK_PAGE } from '../urls'; +import { HOSTS_PAGE, HOSTS_PAGE_TAB_URLS, NETWORK_PAGE, NETWORK_TAB_URLS } from '../urls'; export const INSPECT_BUTTON_ICON = '[data-test-subj="inspect-icon-button"]'; export const INSPECT_MODAL = '[data-test-subj="modal-inspect-euiModal"]'; @@ -72,7 +72,7 @@ export const INSPECT_BUTTONS_IN_SIEM: InspectButtonMetadata[] = [ { id: '[data-test-subj="table-dns-loading-false"]', title: 'Top DNS Domains Table', - url: NETWORK_PAGE, + url: NETWORK_TAB_URLS.dns, }, { id: '[data-test-subj="table-allHosts-loading-false"]', @@ -90,7 +90,7 @@ export const INSPECT_BUTTONS_IN_SIEM: InspectButtonMetadata[] = [ url: HOSTS_PAGE_TAB_URLS.uncommonProcesses, }, { - altInspectId: `[data-test-subj="events-viewer-header"] ${INSPECT_BUTTON_ICON}`, + altInspectId: `[data-test-subj="events-viewer-panel"] ${INSPECT_BUTTON_ICON}`, id: '[data-test-subj="events-container-loading-false"]', title: 'Events Table', url: HOSTS_PAGE_TAB_URLS.events, diff --git a/x-pack/legacy/plugins/siem/cypress/integration/lib/urls/index.ts b/x-pack/legacy/plugins/siem/cypress/integration/lib/urls/index.ts index ac0130495ba7a..18276580289c7 100644 --- a/x-pack/legacy/plugins/siem/cypress/integration/lib/urls/index.ts +++ b/x-pack/legacy/plugins/siem/cypress/integration/lib/urls/index.ts @@ -19,6 +19,9 @@ export const LOGIN_PAGE = '/login'; /** The SIEM app's Network page */ export const NETWORK_PAGE = '/app/siem#/network'; +export const NETWORK_TAB_URLS = { + dns: `${NETWORK_PAGE}/dns`, +}; /** The SIEM app's Overview page */ export const OVERVIEW_PAGE = '/app/siem#/overview'; From 3eea7284ef8d45d325093b624255662bf0258c15 Mon Sep 17 00:00:00 2001 From: Liza Katz Date: Thu, 14 Nov 2019 13:06:36 +0200 Subject: [PATCH 4/9] =?UTF-8?q?Move=20query=20utils=20=E2=87=92=20NP=20(#4?= =?UTF-8?q?9636)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Move query utils to NP * Updated Query imports * A few import fixes * Fix import * Fix docs --- .sass-lint.yml | 1 - src/core/MIGRATION.md | 2 +- src/legacy/core_plugins/data/public/index.ts | 2 +- src/legacy/core_plugins/data/public/mocks.ts | 2 - src/legacy/core_plugins/data/public/plugin.ts | 6 -- .../core_plugins/data/public/query/index.ts | 2 +- .../fetch_index_patterns.ts | 0 .../components/query_bar_input.test.mocks.ts | 2 +- .../query_bar/components/query_bar_input.tsx | 9 ++- .../components/query_bar_top_row.tsx | 10 ++- .../data/public/query/query_bar/index.ts | 6 -- .../query_bar/lib/__tests__/lib_user_input.js | 80 ------------------- .../data/public/query/query_service.mock.ts | 51 ------------ .../data/public/query/query_service.ts | 50 ------------ .../search_bar/components/search_bar.tsx | 5 +- .../data/public/search/search_bar/index.tsx | 4 +- .../kibana/public/dashboard/dashboard_app.tsx | 4 +- .../dashboard/dashboard_app_controller.tsx | 3 +- .../dashboard/dashboard_state_manager.ts | 2 +- .../migrations/move_filters_to_query.ts | 3 +- .../saved_dashboard/saved_dashboard.d.ts | 4 +- .../kibana/public/dashboard/types.ts | 3 +- .../discover/embeddable/search_embeddable.ts | 2 +- .../public/discover/embeddable/types.ts | 4 +- .../embeddable/visualize_embeddable.ts | 4 +- .../public/vis/timelion_request_handler.ts | 3 +- .../public/vega_request_handler.ts | 6 +- .../ui/public/agg_types/buckets/filters.ts | 3 +- .../ui/public/utils/migrate_legacy_query.ts | 2 +- .../vis/editors/default/controls/filter.tsx | 3 +- .../vis/editors/default/controls/filters.tsx | 2 +- .../loader/utils/query_geohash_bounds.ts | 3 +- .../public/embeddable/dashboard_container.tsx | 3 +- src/plugins/data/public/query/index.tsx | 2 + .../data/public/query/lib/from_user.test.ts | 45 +++++++++++ .../data/public/query}/lib/from_user.ts | 4 + .../data/public/query}/lib/get_query_log.ts | 2 +- .../data/public/query}/lib/index.ts | 2 + .../data/public/query}/lib/match_pairs.ts | 0 .../data/public/query/lib/to_user.test.ts | 46 +++++++++++ .../data/public/query}/lib/to_user.ts | 6 +- .../graph/public/components/search_bar.tsx | 7 +- .../plugins/lens/public/app_plugin/app.tsx | 3 +- .../editor_frame/editor_frame.tsx | 4 +- .../editor_frame/expression_helpers.ts | 4 +- .../embeddable/embeddable.test.tsx | 3 +- .../embeddable/embeddable.tsx | 4 +- .../embeddable/expression_wrapper.tsx | 3 +- .../full_time_range_selector.test.tsx | 2 +- .../full_time_range_selector.tsx | 2 +- .../full_time_range_selector_service.ts | 2 +- 51 files changed, 157 insertions(+), 270 deletions(-) rename src/legacy/core_plugins/data/public/query/query_bar/{lib => components}/fetch_index_patterns.ts (100%) delete mode 100644 src/legacy/core_plugins/data/public/query/query_bar/lib/__tests__/lib_user_input.js delete mode 100644 src/legacy/core_plugins/data/public/query/query_service.mock.ts delete mode 100644 src/legacy/core_plugins/data/public/query/query_service.ts create mode 100644 src/plugins/data/public/query/lib/from_user.test.ts rename src/{legacy/core_plugins/data/public/query/query_bar => plugins/data/public/query}/lib/from_user.ts (96%) rename src/{legacy/core_plugins/data/public/query/query_bar => plugins/data/public/query}/lib/get_query_log.ts (94%) rename src/{legacy/core_plugins/data/public/query/query_bar => plugins/data/public/query}/lib/index.ts (93%) rename src/{legacy/core_plugins/data/public/query/query_bar => plugins/data/public/query}/lib/match_pairs.ts (100%) create mode 100644 src/plugins/data/public/query/lib/to_user.test.ts rename src/{legacy/core_plugins/data/public/query/query_bar => plugins/data/public/query}/lib/to_user.ts (89%) diff --git a/.sass-lint.yml b/.sass-lint.yml index 64309aaae6cc3..f6c0f5bb83fcb 100644 --- a/.sass-lint.yml +++ b/.sass-lint.yml @@ -2,7 +2,6 @@ files: include: - 'src/legacy/core_plugins/metrics/**/*.s+(a|c)ss' - 'src/legacy/core_plugins/timelion/**/*.s+(a|c)ss' - - 'src/legacy/ui/public/query_bar/**/*.s+(a|c)ss' - 'src/legacy/ui/public/vislib/**/*.s+(a|c)ss' - 'x-pack/legacy/plugins/rollup/**/*.s+(a|c)ss' - 'x-pack/legacy/plugins/security/**/*.s+(a|c)ss' diff --git a/src/core/MIGRATION.md b/src/core/MIGRATION.md index c26a383719fa1..366a5b65fbb99 100644 --- a/src/core/MIGRATION.md +++ b/src/core/MIGRATION.md @@ -1130,7 +1130,7 @@ import { setup, start } from '../core_plugins/visualizations/public/legacy'; | ------------------------------------------------- | ------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------ | | `import 'ui/apply_filters'` | `import { ApplyFiltersPopover } from '../data/public'` | `import '../data/public/legacy` should be called to load legacy directives | | `import 'ui/filter_bar'` | `import { FilterBar } from '../data/public'` | `import '../data/public/legacy` should be called to load legacy directives | -| `import 'ui/query_bar'` | `import { QueryBar, QueryBarInput } from '../data/public'` | Directives are deprecated. | +| `import 'ui/query_bar'` | `import { QueryBarInput } from '../data/public'` | Directives are deprecated. | | `import 'ui/search_bar'` | `import { SearchBar } from '../data/public'` | Directive is deprecated. | | `import 'ui/kbn_top_nav'` | `import { TopNavMenu } from '../navigation/public'` | Directive is still available in `ui/kbn_top_nav`. | | `ui/saved_objects/components/saved_object_finder` | `import { SavedObjectFinder } from '../kibana_react/public'` | | diff --git a/src/legacy/core_plugins/data/public/index.ts b/src/legacy/core_plugins/data/public/index.ts index c3892fa581fc4..2412541e8c5c8 100644 --- a/src/legacy/core_plugins/data/public/index.ts +++ b/src/legacy/core_plugins/data/public/index.ts @@ -38,7 +38,7 @@ export { IndexPatterns, StaticIndexPattern, } from './index_patterns'; -export { Query, QueryBarInput } from './query'; +export { QueryBarInput } from './query'; export { SearchBar, SearchBarProps, SavedQueryAttributes, SavedQuery } from './search'; /** @public static code */ diff --git a/src/legacy/core_plugins/data/public/mocks.ts b/src/legacy/core_plugins/data/public/mocks.ts index d3b5944127965..39d1296ddf8bc 100644 --- a/src/legacy/core_plugins/data/public/mocks.ts +++ b/src/legacy/core_plugins/data/public/mocks.ts @@ -18,12 +18,10 @@ */ import { indexPatternsServiceMock } from './index_patterns/index_patterns_service.mock'; -import { queryServiceMock } from './query/query_service.mock'; function createDataSetupMock() { return { indexPatterns: indexPatternsServiceMock.createSetupContract(), - query: queryServiceMock.createSetupContract(), }; } diff --git a/src/legacy/core_plugins/data/public/plugin.ts b/src/legacy/core_plugins/data/public/plugin.ts index 76beb4ee56053..2059f61fde59e 100644 --- a/src/legacy/core_plugins/data/public/plugin.ts +++ b/src/legacy/core_plugins/data/public/plugin.ts @@ -19,7 +19,6 @@ import { CoreSetup, CoreStart, Plugin } from 'kibana/public'; import { SearchService, SearchStart, createSearchBar, StatetfulSearchBarProps } from './search'; -import { QueryService, QuerySetup } from './query'; import { IndexPatternsService, IndexPatternsSetup, IndexPatternsStart } from './index_patterns'; import { Storage, IStorageWrapper } from '../../../../../src/plugins/kibana_utils/public'; import { DataPublicPluginStart } from '../../../../plugins/data/public'; @@ -42,7 +41,6 @@ export interface DataPluginStartDependencies { * @public */ export interface DataSetup { - query: QuerySetup; indexPatterns: IndexPatternsSetup; } @@ -52,7 +50,6 @@ export interface DataSetup { * @public */ export interface DataStart { - query: QuerySetup; indexPatterns: IndexPatternsStart; search: SearchStart; ui: { @@ -74,7 +71,6 @@ export interface DataStart { export class DataPlugin implements Plugin { private readonly indexPatterns: IndexPatternsService = new IndexPatternsService(); - private readonly query: QueryService = new QueryService(); private readonly search: SearchService = new SearchService(); private setupApi!: DataSetup; @@ -85,7 +81,6 @@ export class DataPlugin implements Plugin PersistedLog: mockPersistedLogFactory, })); -jest.mock('../lib/fetch_index_patterns', () => ({ +jest.mock('./fetch_index_patterns', () => ({ fetchIndexPatterns: mockFetchIndexPatterns, })); diff --git a/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_input.tsx b/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_input.tsx index 77c9169d03aa4..31a17315db7dd 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_input.tsx +++ b/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_input.tsx @@ -38,6 +38,11 @@ import { AutocompleteSuggestion, AutocompleteSuggestionType, PersistedLog, + toUser, + fromUser, + matchPairs, + getQueryLog, + Query, } from '../../../../../../../plugins/data/public'; import { withKibana, @@ -45,12 +50,10 @@ import { toMountPoint, } from '../../../../../../../plugins/kibana_react/public'; import { IndexPattern, StaticIndexPattern } from '../../../index_patterns'; -import { Query, getQueryLog } from '../index'; -import { fromUser, matchPairs, toUser } from '../lib'; import { QueryLanguageSwitcher } from './language_switcher'; import { SuggestionsComponent } from './typeahead/suggestions_component'; -import { fetchIndexPatterns } from '../lib/fetch_index_patterns'; import { IDataPluginServices } from '../../../types'; +import { fetchIndexPatterns } from './fetch_index_patterns'; interface Props { kibana: KibanaReactContextValue; diff --git a/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_top_row.tsx b/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_top_row.tsx index 9bb8e3875a3d3..ca0ac3c371849 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_top_row.tsx +++ b/src/legacy/core_plugins/data/public/query/query_bar/components/query_bar_top_row.tsx @@ -35,13 +35,17 @@ import { import { EuiSuperUpdateButton, OnRefreshProps } from '@elastic/eui'; import { FormattedMessage, InjectedIntl, injectI18n } from '@kbn/i18n/react'; import { Toast } from 'src/core/public'; -import { TimeRange, TimeHistoryContract } from 'src/plugins/data/public'; +import { + TimeRange, + TimeHistoryContract, + Query, + PersistedLog, + getQueryLog, +} from '../../../../../../../plugins/data/public'; import { useKibana, toMountPoint } from '../../../../../../../plugins/kibana_react/public'; -import { PersistedLog } from '../../../../../../../plugins/data/public'; import { IndexPattern } from '../../../index_patterns'; import { QueryBarInput } from './query_bar_input'; -import { Query, getQueryLog } from '../index'; import { IDataPluginServices } from '../../../types'; interface Props { diff --git a/src/legacy/core_plugins/data/public/query/query_bar/index.ts b/src/legacy/core_plugins/data/public/query/query_bar/index.ts index ece45c5bbd5da..f0ad0707c699a 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/index.ts +++ b/src/legacy/core_plugins/data/public/query/query_bar/index.ts @@ -19,9 +19,3 @@ export { QueryBarTopRow } from './components/query_bar_top_row'; export { QueryBarInput } from './components/query_bar_input'; - -export { fromUser } from './lib/from_user'; -export { toUser } from './lib/to_user'; -export { getQueryLog } from './lib/get_query_log'; - -export { Query } from '../../../../../../plugins/data/public'; diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/__tests__/lib_user_input.js b/src/legacy/core_plugins/data/public/query/query_bar/lib/__tests__/lib_user_input.js deleted file mode 100644 index ef98f3d07c5b9..0000000000000 --- a/src/legacy/core_plugins/data/public/query/query_bar/lib/__tests__/lib_user_input.js +++ /dev/null @@ -1,80 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import expect from '@kbn/expect'; - -import { toUser, fromUser } from '../'; - -describe('user input helpers', function () { - - describe('user input parser', function () { - - it('should return the input if passed an object', function () { - expect(fromUser({ foo: 'bar' })).to.eql({ foo: 'bar' }); - }); - - it('unless the object is empty, then convert it to an empty string', function () { - expect(fromUser({})).to.eql(''); - }); - - it('should pass through input strings that not start with {', function () { - expect(fromUser('foo')).to.eql('foo'); - expect(fromUser('400')).to.eql('400'); - expect(fromUser('true')).to.eql('true'); - }); - - it('should parse valid JSON and return the object instead of a string', function () { - expect(fromUser('{}')).to.eql({}); - - // invalid json remains a string - expect(fromUser('{a:b}')).to.eql('{a:b}'); - }); - }); - - describe('model presentation formatter', function () { - it('should present undefined as empty string', function () { - let notDefined; - expect(toUser(notDefined)).to.be(''); - }); - - it('should present null as empty string', function () { - expect(toUser(null)).to.be(''); - }); - - it('should present objects as strings', function () { - expect(toUser({ foo: 'bar' })).to.be('{"foo":"bar"}'); - }); - - it('should present query_string queries as strings', function () { - expect(toUser({ query_string: { query: 'lucene query string' } })).to.be('lucene query string'); - }); - - it('should present query_string queries without a query as an empty string', function () { - expect(toUser({ query_string: {} })).to.be(''); - }); - - it('should present string as strings', function () { - expect(toUser('foo')).to.be('foo'); - }); - - it('should present numbers as strings', function () { - expect(toUser(400)).to.be('400'); - }); - }); -}); diff --git a/src/legacy/core_plugins/data/public/query/query_service.mock.ts b/src/legacy/core_plugins/data/public/query/query_service.mock.ts deleted file mode 100644 index 19a00632ca192..0000000000000 --- a/src/legacy/core_plugins/data/public/query/query_service.mock.ts +++ /dev/null @@ -1,51 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import { QueryService, QuerySetup } from '.'; - -type QueryServiceClientContract = PublicMethodsOf; - -const createSetupContractMock = () => { - const setupContract: jest.Mocked = { - helpers: { - fromUser: jest.fn(), - toUser: jest.fn(), - getQueryLog: jest.fn(), - }, - }; - - return setupContract; -}; - -const createMock = () => { - const mocked: jest.Mocked = { - setup: jest.fn(), - start: jest.fn(), - stop: jest.fn(), - }; - - mocked.setup.mockReturnValue(createSetupContractMock()); - return mocked; -}; - -export const queryServiceMock = { - create: createMock, - createSetupContract: createSetupContractMock, - createStartContract: createSetupContractMock, -}; diff --git a/src/legacy/core_plugins/data/public/query/query_service.ts b/src/legacy/core_plugins/data/public/query/query_service.ts deleted file mode 100644 index f6f229496f49d..0000000000000 --- a/src/legacy/core_plugins/data/public/query/query_service.ts +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Licensed to Elasticsearch B.V. under one or more contributor - * license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright - * ownership. Elasticsearch B.V. licenses this file to you under - * the Apache License, Version 2.0 (the "License"); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -import { fromUser, toUser, getQueryLog } from './query_bar'; - -/** - * Query Service - * - * @internal - */ -export class QueryService { - public setup() { - return { - helpers: { - fromUser, - toUser, - getQueryLog, - }, - }; - } - - public start() { - // nothing to do here yet - } - - public stop() { - // nothing to do here yet - } -} - -/** @public */ -export type QuerySetup = ReturnType; - -export * from './query_bar'; diff --git a/src/legacy/core_plugins/data/public/search/search_bar/components/search_bar.tsx b/src/legacy/core_plugins/data/public/search/search_bar/components/search_bar.tsx index a57b7b17a0da6..ea0f6775e4831 100644 --- a/src/legacy/core_plugins/data/public/search/search_bar/components/search_bar.tsx +++ b/src/legacy/core_plugins/data/public/search/search_bar/components/search_bar.tsx @@ -24,9 +24,8 @@ import React, { Component } from 'react'; import ResizeObserver from 'resize-observer-polyfill'; import { get, isEqual } from 'lodash'; -import { TimeRange } from 'src/plugins/data/common/types'; -import { TimeHistoryContract } from 'src/plugins/data/public'; -import { IndexPattern, Query, FilterBar } from '../../../../../data/public'; +import { TimeRange, Query, TimeHistoryContract } from 'src/plugins/data/public'; +import { IndexPattern, FilterBar } from '../../../../../data/public'; import { QueryBarTopRow } from '../../../query'; import { SavedQuery, SavedQueryAttributes } from '../index'; import { SavedQueryMeta, SaveQueryForm } from './saved_query_management/save_query_form'; diff --git a/src/legacy/core_plugins/data/public/search/search_bar/index.tsx b/src/legacy/core_plugins/data/public/search/search_bar/index.tsx index ebde9d60b0b51..f369bf997c1a9 100644 --- a/src/legacy/core_plugins/data/public/search/search_bar/index.tsx +++ b/src/legacy/core_plugins/data/public/search/search_bar/index.tsx @@ -17,9 +17,7 @@ * under the License. */ -import { RefreshInterval, TimeRange } from 'src/plugins/data/public'; -import { Query } from '../../query/query_bar'; -import { esFilters } from '../../../../../../plugins/data/public'; +import { RefreshInterval, TimeRange, Query, esFilters } from 'src/plugins/data/public'; export * from './components'; diff --git a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app.tsx b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app.tsx index 5fa3a938ed9df..b9825ceeecdb6 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app.tsx +++ b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app.tsx @@ -35,10 +35,10 @@ import { } from 'ui/state_management/app_state'; import { KbnUrl } from 'ui/url/kbn_url'; -import { TimeRange } from 'src/plugins/data/public'; +import { TimeRange, Query } from 'src/plugins/data/public'; import { IndexPattern } from 'ui/index_patterns'; import { IPrivate } from 'ui/private'; -import { StaticIndexPattern, Query, SavedQuery } from 'plugins/data'; +import { StaticIndexPattern, SavedQuery } from 'plugins/data'; import moment from 'moment'; import { Subscription } from 'rxjs'; diff --git a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app_controller.tsx b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app_controller.tsx index 548a66297a3f9..d82b89339b0d0 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app_controller.tsx +++ b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_app_controller.tsx @@ -50,12 +50,13 @@ import { import { KbnUrl } from 'ui/url/kbn_url'; import { IndexPattern } from 'ui/index_patterns'; import { IPrivate } from 'ui/private'; -import { Query, SavedQuery } from 'src/legacy/core_plugins/data/public'; +import { SavedQuery } from 'src/legacy/core_plugins/data/public'; import { SaveOptions } from 'ui/saved_objects/saved_object'; import { capabilities } from 'ui/capabilities'; import { Subscription } from 'rxjs'; import { npStart } from 'ui/new_platform'; import { SavedObjectFinder } from 'ui/saved_objects/components/saved_object_finder'; +import { Query } from '../../../../../plugins/data/public'; import { start as data } from '../../../data/public/legacy'; import { diff --git a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_state_manager.ts b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_state_manager.ts index 8ffabe5add1c3..1a42ed837a9de 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/dashboard_state_manager.ts +++ b/src/legacy/core_plugins/kibana/public/dashboard/dashboard_state_manager.ts @@ -27,9 +27,9 @@ import { migrateLegacyQuery } from 'ui/utils/migrate_legacy_query'; import { Moment } from 'moment'; import { DashboardContainer } from 'src/legacy/core_plugins/dashboard_embeddable_container/public/np_ready/public'; +import { Query } from 'src/plugins/data/public'; import { ViewMode } from '../../../../../../src/plugins/embeddable/public'; import { esFilters } from '../../../../../../src/plugins/data/public'; -import { Query } from '../../../data/public'; import { getAppStateDefaults, migrateAppState } from './lib'; import { convertPanelStateToSavedDashboardPanel } from './lib/embeddable_saved_object_converters'; diff --git a/src/legacy/core_plugins/kibana/public/dashboard/migrations/move_filters_to_query.ts b/src/legacy/core_plugins/kibana/public/dashboard/migrations/move_filters_to_query.ts index 8522495b9dedb..e82fc58670e39 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/migrations/move_filters_to_query.ts +++ b/src/legacy/core_plugins/kibana/public/dashboard/migrations/move_filters_to_query.ts @@ -17,8 +17,7 @@ * under the License. */ -import { Query } from 'src/legacy/core_plugins/data/public'; -import { esFilters } from '../../../../../../plugins/data/public'; +import { esFilters, Query } from '../../../../../../plugins/data/public'; export interface Pre600FilterQuery { // pre 6.0.0 global query:queryString:options were stored per dashboard and would diff --git a/src/legacy/core_plugins/kibana/public/dashboard/saved_dashboard/saved_dashboard.d.ts b/src/legacy/core_plugins/kibana/public/dashboard/saved_dashboard/saved_dashboard.d.ts index 5b860b0a2cc7c..5b24aa13f4f77 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/saved_dashboard/saved_dashboard.d.ts +++ b/src/legacy/core_plugins/kibana/public/dashboard/saved_dashboard/saved_dashboard.d.ts @@ -19,9 +19,7 @@ import { SearchSource } from 'ui/courier'; import { SavedObject } from 'ui/saved_objects/saved_object'; -import { RefreshInterval } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; -import { esFilters } from '../../../../../../plugins/data/public'; +import { esFilters, Query, RefreshInterval } from '../../../../../../plugins/data/public'; export interface SavedObjectDashboard extends SavedObject { id?: string; diff --git a/src/legacy/core_plugins/kibana/public/dashboard/types.ts b/src/legacy/core_plugins/kibana/public/dashboard/types.ts index 5aaca7b62094f..3c2c87a502da4 100644 --- a/src/legacy/core_plugins/kibana/public/dashboard/types.ts +++ b/src/legacy/core_plugins/kibana/public/dashboard/types.ts @@ -18,7 +18,6 @@ */ import { AppState } from 'ui/state_management/app_state'; -import { Query } from 'src/legacy/core_plugins/data/public'; import { AppState as TAppState } from 'ui/state_management/app_state'; import { ViewMode } from 'src/plugins/embeddable/public'; import { @@ -29,7 +28,7 @@ import { RawSavedDashboardPanel640To720, RawSavedDashboardPanel730ToLatest, } from './migrations/types'; -import { esFilters } from '../../../../../plugins/data/public'; +import { Query, esFilters } from '../../../../../plugins/data/public'; export type NavAction = (anchorElement?: any) => void; diff --git a/src/legacy/core_plugins/kibana/public/discover/embeddable/search_embeddable.ts b/src/legacy/core_plugins/kibana/public/discover/embeddable/search_embeddable.ts index 732fb6d2e4e70..d719864d99447 100644 --- a/src/legacy/core_plugins/kibana/public/discover/embeddable/search_embeddable.ts +++ b/src/legacy/core_plugins/kibana/public/discover/embeddable/search_embeddable.ts @@ -27,8 +27,8 @@ import { TimeRange, onlyDisabledFiltersChanged, getTime, + Query, } from '../../../../../../plugins/data/public'; -import { Query } from '../../../../data/public'; import { APPLY_FILTER_TRIGGER, Container, diff --git a/src/legacy/core_plugins/kibana/public/discover/embeddable/types.ts b/src/legacy/core_plugins/kibana/public/discover/embeddable/types.ts index 5473ec0e7b8b4..2d940ad8cba98 100644 --- a/src/legacy/core_plugins/kibana/public/discover/embeddable/types.ts +++ b/src/legacy/core_plugins/kibana/public/discover/embeddable/types.ts @@ -17,13 +17,11 @@ * under the License. */ -import { TimeRange } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; import { EmbeddableInput, EmbeddableOutput, IEmbeddable } from 'src/plugins/embeddable/public'; import { StaticIndexPattern } from '../kibana_services'; import { SavedSearch } from '../types'; import { SortOrder } from '../angular/doc_table/components/table_header/helpers'; -import { esFilters } from '../../../../../../plugins/data/public'; +import { esFilters, TimeRange, Query } from '../../../../../../plugins/data/public'; export interface SearchInput extends EmbeddableInput { timeRange: TimeRange; diff --git a/src/legacy/core_plugins/kibana/public/visualize/embeddable/visualize_embeddable.ts b/src/legacy/core_plugins/kibana/public/visualize/embeddable/visualize_embeddable.ts index 60cf7c7ec1928..0b75c6ffa1ffb 100644 --- a/src/legacy/core_plugins/kibana/public/visualize/embeddable/visualize_embeddable.ts +++ b/src/legacy/core_plugins/kibana/public/visualize/embeddable/visualize_embeddable.ts @@ -33,11 +33,12 @@ import { npStart } from 'ui/new_platform'; import { IExpressionLoaderParams } from '../../../../expressions/public/np_ready/public/types'; import { start as expressions } from '../../../../expressions/public/legacy'; import { VISUALIZE_EMBEDDABLE_TYPE } from './constants'; -import { Query } from '../../../../data/public'; import { TimeRange, + Query, onlyDisabledFiltersChanged, esFilters, + mapAndFlattenFilters, } from '../../../../../../plugins/data/public'; import { EmbeddableInput, @@ -47,7 +48,6 @@ import { APPLY_FILTER_TRIGGER, } from '../../../../../../plugins/embeddable/public'; import { dispatchRenderComplete } from '../../../../../../plugins/kibana_utils/public'; -import { mapAndFlattenFilters } from '../../../../../../plugins/data/public'; const getKeys = (o: T): Array => Object.keys(o) as Array; diff --git a/src/legacy/core_plugins/timelion/public/vis/timelion_request_handler.ts b/src/legacy/core_plugins/timelion/public/vis/timelion_request_handler.ts index 6239e4027c392..35dea4a0deb9b 100644 --- a/src/legacy/core_plugins/timelion/public/vis/timelion_request_handler.ts +++ b/src/legacy/core_plugins/timelion/public/vis/timelion_request_handler.ts @@ -22,8 +22,7 @@ import { buildEsQuery, getEsQueryConfig } from '@kbn/es-query'; // @ts-ignore import { timezoneProvider } from 'ui/vis/lib/timezone'; import { KIBANA_CONTEXT_NAME } from 'src/plugins/expressions/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; -import { TimeRange, esFilters } from 'src/plugins/data/public'; +import { Query, TimeRange, esFilters } from 'src/plugins/data/public'; import { VisParams } from 'ui/vis'; import { i18n } from '@kbn/i18n'; import { TimelionVisualizationDependencies } from '../plugin'; diff --git a/src/legacy/core_plugins/vis_type_vega/public/vega_request_handler.ts b/src/legacy/core_plugins/vis_type_vega/public/vega_request_handler.ts index b4c32f37eb90c..accc52c1e5a14 100644 --- a/src/legacy/core_plugins/vis_type_vega/public/vega_request_handler.ts +++ b/src/legacy/core_plugins/vis_type_vega/public/vega_request_handler.ts @@ -18,11 +18,9 @@ */ import { timefilter } from 'ui/timefilter'; -import { TimeRange } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; -import { buildEsQuery, getEsQueryConfig } from '@kbn/es-query'; -import { esFilters } from '../../../../plugins/data/public'; +import { buildEsQuery, getEsQueryConfig } from '@kbn/es-query'; +import { esFilters, TimeRange, Query } from '../../../../plugins/data/public'; // @ts-ignore import { VegaParser } from './data_model/vega_parser'; diff --git a/src/legacy/ui/public/agg_types/buckets/filters.ts b/src/legacy/ui/public/agg_types/buckets/filters.ts index 44a97abb7a1d7..a8d509d507c6b 100644 --- a/src/legacy/ui/public/agg_types/buckets/filters.ts +++ b/src/legacy/ui/public/agg_types/buckets/filters.ts @@ -27,10 +27,9 @@ import { buildEsQuery } from '@kbn/es-query'; import { FiltersParamEditor, FilterValue } from '../../vis/editors/default/controls/filters'; import { createFilterFilters } from './create_filter/filters'; import { BucketAggType, IBucketAggConfig } from './_bucket_agg_type'; -import { setup as data } from '../../../../core_plugins/data/public/legacy'; import { Storage } from '../../../../../plugins/kibana_utils/public'; +import { getQueryLog } from '../../../../../plugins/data/public'; -const { getQueryLog } = data.query.helpers; const config = chrome.getUiSettingsClient(); const storage = new Storage(window.localStorage); diff --git a/src/legacy/ui/public/utils/migrate_legacy_query.ts b/src/legacy/ui/public/utils/migrate_legacy_query.ts index 06e819d6a64a2..8d9b50d5a66b2 100644 --- a/src/legacy/ui/public/utils/migrate_legacy_query.ts +++ b/src/legacy/ui/public/utils/migrate_legacy_query.ts @@ -18,7 +18,7 @@ */ import { has } from 'lodash'; -import { Query } from 'plugins/data'; +import { Query } from 'src/plugins/data/public'; /** * Creates a standardized query object from old queries that were either strings or pure ES query DSL diff --git a/src/legacy/ui/public/vis/editors/default/controls/filter.tsx b/src/legacy/ui/public/vis/editors/default/controls/filter.tsx index 4ebe7b0d835d7..e847a95ead478 100644 --- a/src/legacy/ui/public/vis/editors/default/controls/filter.tsx +++ b/src/legacy/ui/public/vis/editors/default/controls/filter.tsx @@ -20,7 +20,8 @@ import React, { useState } from 'react'; import { EuiForm, EuiButtonIcon, EuiFieldText, EuiFormRow, EuiSpacer } from '@elastic/eui'; import { i18n } from '@kbn/i18n'; -import { Query, QueryBarInput } from 'plugins/data'; +import { QueryBarInput } from 'plugins/data'; +import { Query } from 'src/plugins/data/public'; import { AggConfig } from '../../..'; import { npStart } from '../../../../new_platform'; import { Storage } from '../../../../../../../plugins/kibana_utils/public'; diff --git a/src/legacy/ui/public/vis/editors/default/controls/filters.tsx b/src/legacy/ui/public/vis/editors/default/controls/filters.tsx index fe72e8dddd68d..aa654d26a23fd 100644 --- a/src/legacy/ui/public/vis/editors/default/controls/filters.tsx +++ b/src/legacy/ui/public/vis/editors/default/controls/filters.tsx @@ -21,7 +21,7 @@ import React, { useState, useEffect } from 'react'; import { omit, isEqual } from 'lodash'; import { htmlIdGenerator, EuiButton, EuiSpacer } from '@elastic/eui'; import { FormattedMessage } from '@kbn/i18n/react'; -import { Query } from 'plugins/data'; +import { Query } from 'src/plugins/data/public'; import chrome from '../../../../chrome'; import { FilterRow } from './filter'; import { AggParamEditorProps } from '..'; diff --git a/src/legacy/ui/public/visualize/loader/utils/query_geohash_bounds.ts b/src/legacy/ui/public/visualize/loader/utils/query_geohash_bounds.ts index 912afab74bef4..36759551a1723 100644 --- a/src/legacy/ui/public/visualize/loader/utils/query_geohash_bounds.ts +++ b/src/legacy/ui/public/visualize/loader/utils/query_geohash_bounds.ts @@ -22,11 +22,10 @@ import { get } from 'lodash'; import { toastNotifications } from 'ui/notify'; import { AggConfig } from 'ui/vis'; -import { Query } from 'src/legacy/core_plugins/data/public'; import { timefilter } from 'ui/timefilter'; import { Vis } from '../../../vis'; +import { esFilters, Query } from '../../../../../../plugins/data/public'; import { SearchSource } from '../../../courier'; -import { esFilters } from '../../../../../../plugins/data/public'; interface QueryGeohashBoundsParams { filters?: esFilters.Filter[]; diff --git a/src/plugins/dashboard_embeddable_container/public/embeddable/dashboard_container.tsx b/src/plugins/dashboard_embeddable_container/public/embeddable/dashboard_container.tsx index 8b258f3558438..6cefd11c912f1 100644 --- a/src/plugins/dashboard_embeddable_container/public/embeddable/dashboard_container.tsx +++ b/src/plugins/dashboard_embeddable_container/public/embeddable/dashboard_container.tsx @@ -20,7 +20,7 @@ import React from 'react'; import ReactDOM from 'react-dom'; import { I18nProvider } from '@kbn/i18n/react'; -import { RefreshInterval, TimeRange, Query } from '../../../data/public'; +import { RefreshInterval, TimeRange, Query, esFilters } from '../../../data/public'; import { CoreStart } from '../../../../core/public'; import { IUiActionsStart } from '../ui_actions_plugin'; import { @@ -37,7 +37,6 @@ import { createPanelState } from './panel'; import { DashboardPanelState } from './types'; import { DashboardViewport } from './viewport/dashboard_viewport'; import { Start as InspectorStartContract } from '../../../inspector/public'; -import { esFilters } from '../../../../plugins/data/public'; import { KibanaContextProvider, KibanaReactContext, diff --git a/src/plugins/data/public/query/index.tsx b/src/plugins/data/public/query/index.tsx index 9d7c2ffc56f70..224c2f3a04076 100644 --- a/src/plugins/data/public/query/index.tsx +++ b/src/plugins/data/public/query/index.tsx @@ -17,6 +17,8 @@ * under the License. */ +export * from './lib'; + export * from './query_service'; export * from './filter_manager'; diff --git a/src/plugins/data/public/query/lib/from_user.test.ts b/src/plugins/data/public/query/lib/from_user.test.ts new file mode 100644 index 0000000000000..b74a1a07dc356 --- /dev/null +++ b/src/plugins/data/public/query/lib/from_user.test.ts @@ -0,0 +1,45 @@ +/* + * Licensed to Elasticsearch B.V. under one or more contributor + * license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright + * ownership. Elasticsearch B.V. licenses this file to you under + * the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import { fromUser } from '../'; + +describe('user input helpers', function() { + describe('user input parser', function() { + it('should return the input if passed an object', function() { + expect(fromUser({ foo: 'bar' })).toEqual({ foo: 'bar' }); + }); + + it('unless the object is empty, then convert it to an empty string', function() { + expect(fromUser({})).toEqual(''); + }); + + it('should pass through input strings that not start with {', function() { + expect(fromUser('foo')).toEqual('foo'); + expect(fromUser('400')).toEqual('400'); + expect(fromUser('true')).toEqual('true'); + }); + + it('should parse valid JSON and return the object instead of a string', function() { + expect(fromUser('{}')).toEqual({}); + + // invalid json remains a string + expect(fromUser('{a:b}')).toEqual('{a:b}'); + }); + }); +}); diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/from_user.ts b/src/plugins/data/public/query/lib/from_user.ts similarity index 96% rename from src/legacy/core_plugins/data/public/query/query_bar/lib/from_user.ts rename to src/plugins/data/public/query/lib/from_user.ts index 15eebaa0b9fd6..fbb1726fc99ea 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/lib/from_user.ts +++ b/src/plugins/data/public/query/lib/from_user.ts @@ -28,6 +28,10 @@ import _ from 'lodash'; export function fromUser(userInput: object | string) { const matchAll = ''; + if (_.isEmpty(userInput)) { + return ''; + } + if (_.isObject(userInput)) { return userInput; } diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/get_query_log.ts b/src/plugins/data/public/query/lib/get_query_log.ts similarity index 94% rename from src/legacy/core_plugins/data/public/query/query_bar/lib/get_query_log.ts rename to src/plugins/data/public/query/lib/get_query_log.ts index 66424d9a1d6a3..67073a9078046 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/lib/get_query_log.ts +++ b/src/plugins/data/public/query/lib/get_query_log.ts @@ -19,7 +19,7 @@ import { UiSettingsClientContract } from 'src/core/public'; import { IStorageWrapper } from 'src/plugins/kibana_utils/public'; -import { PersistedLog } from '../../../../../../../plugins/data/public'; +import { PersistedLog } from '../persisted_log'; export function getQueryLog( uiSettings: UiSettingsClientContract, diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/index.ts b/src/plugins/data/public/query/lib/index.ts similarity index 93% rename from src/legacy/core_plugins/data/public/query/query_bar/lib/index.ts rename to src/plugins/data/public/query/lib/index.ts index 852f9fd269b32..19ac37fb59ae7 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/lib/index.ts +++ b/src/plugins/data/public/query/lib/index.ts @@ -20,3 +20,5 @@ export * from './match_pairs'; export * from './from_user'; export * from './to_user'; +export * from './to_user'; +export * from './get_query_log'; diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/match_pairs.ts b/src/plugins/data/public/query/lib/match_pairs.ts similarity index 100% rename from src/legacy/core_plugins/data/public/query/query_bar/lib/match_pairs.ts rename to src/plugins/data/public/query/lib/match_pairs.ts diff --git a/src/plugins/data/public/query/lib/to_user.test.ts b/src/plugins/data/public/query/lib/to_user.test.ts new file mode 100644 index 0000000000000..d13afa251ecb1 --- /dev/null +++ b/src/plugins/data/public/query/lib/to_user.test.ts @@ -0,0 +1,46 @@ +/* + * Licensed to Elasticsearch B.V. under one or more contributor + * license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright + * ownership. Elasticsearch B.V. licenses this file to you under + * the Apache License, Version 2.0 (the "License"); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import { toUser } from '../'; + +describe('user input helpers', function() { + describe('model presentation formatter', function() { + it('should present objects as strings', function() { + expect(toUser({ foo: 'bar' })).toBe('{"foo":"bar"}'); + }); + + it('should present query_string queries as strings', function() { + expect(toUser({ query_string: { query: 'lucene query string' } })).toBe( + 'lucene query string' + ); + }); + + it('should present query_string queries without a query as an empty string', function() { + expect(toUser({ query_string: {} })).toBe(''); + }); + + it('should present string as strings', function() { + expect(toUser('foo')).toBe('foo'); + }); + + it('should present numbers as strings', function() { + expect(toUser(400)).toBe('400'); + }); + }); +}); diff --git a/src/legacy/core_plugins/data/public/query/query_bar/lib/to_user.ts b/src/plugins/data/public/query/lib/to_user.ts similarity index 89% rename from src/legacy/core_plugins/data/public/query/query_bar/lib/to_user.ts rename to src/plugins/data/public/query/lib/to_user.ts index 1eb054ba40514..1fdb2d8ed03df 100644 --- a/src/legacy/core_plugins/data/public/query/query_bar/lib/to_user.ts +++ b/src/plugins/data/public/query/lib/to_user.ts @@ -17,14 +17,12 @@ * under the License. */ -import angular from 'angular'; - /** * Take text from the model and present it to the user as a string * @param text model value * @returns {string} */ -export function toUser(text: { [key: string]: any } | string): string { +export function toUser(text: { [key: string]: any } | string | number): string { if (text == null) { return ''; } @@ -35,7 +33,7 @@ export function toUser(text: { [key: string]: any } | string): string { if (text.query_string) { return toUser(text.query_string.query); } - return angular.toJson(text); + return JSON.stringify(text); } return '' + text; } diff --git a/x-pack/legacy/plugins/graph/public/components/search_bar.tsx b/x-pack/legacy/plugins/graph/public/components/search_bar.tsx index d8576c02d29c9..293219cca9876 100644 --- a/x-pack/legacy/plugins/graph/public/components/search_bar.tsx +++ b/x-pack/legacy/plugins/graph/public/components/search_bar.tsx @@ -11,12 +11,9 @@ import { i18n } from '@kbn/i18n'; import { connect } from 'react-redux'; import { fromKueryExpression, toElasticsearchQuery } from '@kbn/es-query'; import { IDataPluginServices } from 'src/legacy/core_plugins/data/public/types'; +import { Query } from 'src/plugins/data/public'; import { IndexPatternSavedObject, IndexPatternProvider } from '../types'; -import { - QueryBarInput, - Query, - IndexPattern, -} from '../../../../../../src/legacy/core_plugins/data/public'; +import { QueryBarInput, IndexPattern } from '../../../../../../src/legacy/core_plugins/data/public'; import { openSourceModal } from '../services/source_modal'; import { diff --git a/x-pack/legacy/plugins/lens/public/app_plugin/app.tsx b/x-pack/legacy/plugins/lens/public/app_plugin/app.tsx index 2815ac9ddda4e..fc5088c1271ad 100644 --- a/x-pack/legacy/plugins/lens/public/app_plugin/app.tsx +++ b/x-pack/legacy/plugins/lens/public/app_plugin/app.tsx @@ -8,7 +8,7 @@ import _ from 'lodash'; import React, { useState, useEffect, useCallback } from 'react'; import { I18nProvider } from '@kbn/i18n/react'; import { i18n } from '@kbn/i18n'; -import { DataPublicPluginStart } from 'src/plugins/data/public'; +import { Query, DataPublicPluginStart } from 'src/plugins/data/public'; import { SavedObjectSaveModal } from 'ui/saved_objects/components/saved_object_save_modal'; import { CoreStart, NotificationsStart } from 'src/core/public'; import { @@ -16,7 +16,6 @@ import { IndexPattern as IndexPatternInstance, IndexPatterns as IndexPatternsService, SavedQuery, - Query, } from 'src/legacy/core_plugins/data/public'; import { IStorageWrapper } from 'src/plugins/kibana_utils/public'; import { start as navigation } from '../../../../../../src/legacy/core_plugins/navigation/public/legacy'; diff --git a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/editor_frame.tsx b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/editor_frame.tsx index 6d782d119525d..fabbb6a5d722a 100644 --- a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/editor_frame.tsx +++ b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/editor_frame.tsx @@ -6,7 +6,6 @@ import React, { useEffect, useReducer } from 'react'; import { CoreSetup, CoreStart } from 'src/core/public'; -import { Query, SavedQuery } from '../../../../../../../src/legacy/core_plugins/data/public'; import { ExpressionRenderer } from '../../../../../../../src/legacy/core_plugins/expressions/public'; import { Datasource, @@ -25,7 +24,8 @@ import { Document } from '../../persistence/saved_object_store'; import { getSavedObjectFormat } from './save'; import { WorkspacePanelWrapper } from './workspace_panel_wrapper'; import { generateId } from '../../id_generator'; -import { esFilters } from '../../../../../../../src/plugins/data/public'; +import { SavedQuery } from '../../../../../../../src/legacy/core_plugins/data/public'; +import { esFilters, Query } from '../../../../../../../src/plugins/data/public'; export interface EditorFrameProps { doc?: Document; diff --git a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/expression_helpers.ts b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/expression_helpers.ts index 6b15bc5c2ef30..19882b15d40a7 100644 --- a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/expression_helpers.ts +++ b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/editor_frame/expression_helpers.ts @@ -4,11 +4,9 @@ * you may not use this file except in compliance with the Elastic License. */ -import { TimeRange } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; import { Ast, fromExpression, ExpressionFunctionAST } from '@kbn/interpreter/common'; import { Visualization, Datasource, FramePublicAPI } from '../../types'; -import { esFilters } from '../../../../../../../src/plugins/data/public'; +import { esFilters, TimeRange, Query } from '../../../../../../../src/plugins/data/public'; export function prependDatasourceExpression( visualizationExpression: Ast | string | null, diff --git a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.test.tsx b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.test.tsx index 95d39409c57de..a1a906553fe74 100644 --- a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.test.tsx +++ b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.test.tsx @@ -5,8 +5,7 @@ */ import { Embeddable } from './embeddable'; -import { TimeRange, esFilters } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; +import { Query, TimeRange, esFilters } from 'src/plugins/data/public'; import { ExpressionRendererProps } from 'src/legacy/core_plugins/expressions/public'; import { Document } from '../../persistence'; diff --git a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.tsx b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.tsx index 0b5d4909c8e73..11b846b3670f9 100644 --- a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.tsx +++ b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/embeddable.tsx @@ -8,8 +8,8 @@ import _ from 'lodash'; import React from 'react'; import { render, unmountComponentAtNode } from 'react-dom'; -import { TimeRange, esFilters } from 'src/plugins/data/public'; -import { Query, StaticIndexPattern } from 'src/legacy/core_plugins/data/public'; +import { Query, TimeRange, esFilters } from 'src/plugins/data/public'; +import { StaticIndexPattern } from 'src/legacy/core_plugins/data/public'; import { ExpressionRenderer } from 'src/legacy/core_plugins/expressions/public'; import { Subscription } from 'rxjs'; import { diff --git a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/expression_wrapper.tsx b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/expression_wrapper.tsx index fc6122821ebf5..b3fadaea0afa0 100644 --- a/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/expression_wrapper.tsx +++ b/x-pack/legacy/plugins/lens/public/editor_frame_plugin/embeddable/expression_wrapper.tsx @@ -9,8 +9,7 @@ import React from 'react'; import { I18nProvider } from '@kbn/i18n/react'; import { FormattedMessage } from '@kbn/i18n/react'; import { EuiFlexGroup, EuiFlexItem, EuiText, EuiIcon } from '@elastic/eui'; -import { TimeRange, esFilters } from 'src/plugins/data/public'; -import { Query } from 'src/legacy/core_plugins/data/public'; +import { TimeRange, esFilters, Query } from 'src/plugins/data/public'; import { ExpressionRenderer } from 'src/legacy/core_plugins/expressions/public'; export interface ExpressionWrapperProps { diff --git a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.test.tsx b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.test.tsx index 4da2a040e9975..38e4a3fc24278 100644 --- a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.test.tsx +++ b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.test.tsx @@ -8,7 +8,7 @@ import React from 'react'; import { shallowWithIntl } from 'test_utils/enzyme_helpers'; import { IndexPattern } from 'ui/index_patterns'; import { FullTimeRangeSelector } from './index'; -import { Query } from 'src/legacy/core_plugins/data/public'; +import { Query } from 'src/plugins/data/public'; // Create a mock for the setFullTimeRange function in the service. // The mock is hoisted to the top, so need to prefix the mock function diff --git a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.tsx b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.tsx index 3c377e4dcb448..f637ffb9beea0 100644 --- a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.tsx +++ b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector.tsx @@ -7,7 +7,7 @@ import React, { FC } from 'react'; import { FormattedMessage } from '@kbn/i18n/react'; -import { Query } from 'src/legacy/core_plugins/data/public'; +import { Query } from 'src/plugins/data/public'; import { IndexPattern } from 'ui/index_patterns'; import { EuiButton } from '@elastic/eui'; import { setFullTimeRange } from './full_time_range_selector_service'; diff --git a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector_service.ts b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector_service.ts index 9ed908f9ffcee..bd31ccf7eca3d 100644 --- a/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector_service.ts +++ b/x-pack/legacy/plugins/ml/public/components/full_time_range_selector/full_time_range_selector_service.ts @@ -10,7 +10,7 @@ import { i18n } from '@kbn/i18n'; import { IndexPattern } from 'ui/index_patterns'; import { toastNotifications } from 'ui/notify'; import { timefilter } from 'ui/timefilter'; -import { Query } from 'src/legacy/core_plugins/data/public'; +import { Query } from 'src/plugins/data/public'; import dateMath from '@elastic/datemath'; import { ml, GetTimeFieldRangeResponse } from '../../services/ml_api_service'; From f24497745b44327181dbba96850eb4b1ff8f7150 Mon Sep 17 00:00:00 2001 From: Dima Arnautov Date: Thu, 14 Nov 2019 12:07:59 +0100 Subject: [PATCH 5/9] [ML] Fix escape special characters for Lucene query language (#50494) * [ML] avoid special characters escaping for Lucene query language * [ML] unit test * [ML] init the callback at the higher scope --- .../ml/public/util/custom_url_utils.test.ts | 39 +++++++++++++++++ .../ml/public/util/custom_url_utils.ts | 42 +++++++++++++------ 2 files changed, 68 insertions(+), 13 deletions(-) diff --git a/x-pack/legacy/plugins/ml/public/util/custom_url_utils.test.ts b/x-pack/legacy/plugins/ml/public/util/custom_url_utils.test.ts index d4556f085f4b2..ff97c3fffbf1c 100644 --- a/x-pack/legacy/plugins/ml/public/util/custom_url_utils.test.ts +++ b/x-pack/legacy/plugins/ml/public/util/custom_url_utils.test.ts @@ -306,6 +306,45 @@ describe('ML - custom URL utils', () => { ); // eslint-disable-line max-len }); + test('does not escape special characters for Lucene query language inside of the filter', () => { + const testUrlLuceneFilters: KibanaUrlConfig = { + url_name: 'Lucene query with filters', + time_range: 'auto', + url_value: + "kibana#/dashboard/884c8780-0618-11ea-b671-c9c7e0ebf1f2?_g=(filters:!(),refreshInterval:(pause:!t,value:0),time:(from:'$earliest$',to:'$latest$'))&_a=(description:'',filters:!(('$state':(store:appState),meta:(alias:!n,disabled:!f,index:'7a0a6120-0612-11ea-b671-c9c7e0ebf1f2',key:'at@name',negate:!f,params:(query:'$at@name$'),type:phrase),query:(match_phrase:('at@name':'$at@name$')))),fullScreenMode:!f,options:(hidePanelTitles:!f,useMargins:!t),panels:!((embeddableConfig:(),gridData:(h:15,i:f7ef89e3-62a6-42da-84b2-c815d8da8bb4,w:24,x:0,y:0),id:'19067710-0617-11ea-b671-c9c7e0ebf1f2',panelIndex:f7ef89e3-62a6-42da-84b2-c815d8da8bb4,type:visualization,version:'8.0.0')),query:(language:lucene,query:''),timeRestore:!f,title:special-lucine,viewMode:view)", // eslint-disable-line max-len + }; + + const testRecord = { + job_id: 'special-chars-job-1', + result_type: 'record', + probability: 0.01460073141268696, + multi_bucket_impact: -5, + record_score: 23.817016191989776, + initial_record_score: 23.817016191989776, + bucket_span: 900, + detector_index: 0, + is_interim: false, + timestamp: 1549548900000, + partition_field_name: 'at@name', + partition_field_value: 'contains\\ and a /', + function: 'mean', + function_description: 'mean', + typical: [998.382636366326], + actual: [903.4208848741321], + field_name: 'metric%$£&!{(]field', + earliest: '2017-02-09T15:10:00.000Z', + latest: '2017-02-09T17:15:00.000Z', + influencers: [ + { influencer_field_name: 'at@name', influencer_field_values: ['contains\\ and a /'] }, + ], + 'at@name': ['contains\\ and a /'], + }; + + expect(getUrlForRecord(testUrlLuceneFilters, testRecord)).toBe( + "kibana#/dashboard/884c8780-0618-11ea-b671-c9c7e0ebf1f2?_g=(filters:!(),refreshInterval:(pause:!t,value:0),time:(from:'2017-02-09T15:10:00.000Z',to:'2017-02-09T17:15:00.000Z'))&_a=(description:'',filters:!(('$state':(store:appState),meta:(alias:!n,disabled:!f,index:'7a0a6120-0612-11ea-b671-c9c7e0ebf1f2',key:'at@name',negate:!f,params:(query:'contains%5C%20and%20a%20%2F'),type:phrase),query:(match_phrase:('at@name':'contains%5C%20and%20a%20%2F')))),fullScreenMode:!f,options:(hidePanelTitles:!f,useMargins:!t),panels:!((embeddableConfig:(),gridData:(h:15,i:f7ef89e3-62a6-42da-84b2-c815d8da8bb4,w:24,x:0,y:0),id:'19067710-0617-11ea-b671-c9c7e0ebf1f2',panelIndex:f7ef89e3-62a6-42da-84b2-c815d8da8bb4,type:visualization,version:'8.0.0')),query:(language:lucene,query:''),timeRestore:!f,title:special-lucine,viewMode:view)" + ); // eslint-disable-line max-len + }); + test('returns expected URL for other type URL', () => { expect(getUrlForRecord(TEST_OTHER_URL, TEST_RECORD)).toBe( 'http://airlinecodes.info/airline-code-AAL' diff --git a/x-pack/legacy/plugins/ml/public/util/custom_url_utils.ts b/x-pack/legacy/plugins/ml/public/util/custom_url_utils.ts index 7fda7a88d318f..0d21aed222cad 100644 --- a/x-pack/legacy/plugins/ml/public/util/custom_url_utils.ts +++ b/x-pack/legacy/plugins/ml/public/util/custom_url_utils.ts @@ -107,39 +107,54 @@ function escapeForKQL(value: string | number): string { return String(value).replace(/\"/g, '\\"'); } -// Builds a Kibana dashboard or Discover URL from the supplied config, with any -// dollar delimited tokens substituted from the supplied anomaly record. +type GetResultTokenValue = (v: string) => string; + +/** + * Builds a Kibana dashboard or Discover URL from the supplied config, with any + * dollar delimited tokens substituted from the supplied anomaly record. + */ function buildKibanaUrl(urlConfig: UrlConfig, record: CustomUrlAnomalyRecordDoc) { const urlValue = urlConfig.url_value; const URL_LENGTH_LIMIT = 2000; - const isLuceneQuery = urlValue.includes('language:lucene'); - const queryLanguageEscapeCallback = isLuceneQuery ? escapeForElasticsearchQuery : escapeForKQL; + const isLuceneQueryLanguage = urlValue.includes('language:lucene'); - type GetResultTokenValue = (v: string) => string; + const queryLanguageEscapeCallback = isLuceneQueryLanguage + ? escapeForElasticsearchQuery + : escapeForKQL; - // Compose callback for characters escaping and encoding. - const getResultTokenValue: GetResultTokenValue = flow( - queryLanguageEscapeCallback, + const commonEscapeCallback = flow( // Kibana URLs used rison encoding, so escape with ! any ! or ' characters (v: string): string => v.replace(/[!']/g, '!$&'), encodeURIComponent ); - const replaceSingleTokenValues = (str: string) => - str.replace(/\$([^?&$\'"]+)\$/g, (match, name: string) => { + const replaceSingleTokenValues = (str: string) => { + const getResultTokenValue: GetResultTokenValue = flow( + // Special characters inside of the filter should not be escaped for Lucene query language. + isLuceneQueryLanguage ? (v: T) => v : queryLanguageEscapeCallback, + commonEscapeCallback + ); + + return str.replace(/\$([^?&$\'"]+)\$/g, (match, name: string) => { // Use lodash get to allow nested JSON fields to be retrieved. let tokenValue: string | string[] | undefined = get(record, name); tokenValue = Array.isArray(tokenValue) ? tokenValue[0] : tokenValue; + // If property not found string is not replaced. return tokenValue === undefined ? match : getResultTokenValue(tokenValue); }); + }; return flow( (str: string) => str.replace('$earliest$', record.earliest).replace('$latest$', record.latest), // Process query string content of the URL - (str: string) => - str.replace( + (str: string) => { + const getResultTokenValue: GetResultTokenValue = flow( + queryLanguageEscapeCallback, + commonEscapeCallback + ); + return str.replace( /(.+query:')([^']*)('.+)/, (fullMatch, prefix: string, queryString: string, postfix: string) => { const [resultPrefix, resultPostfix] = [prefix, postfix].map(replaceSingleTokenValues); @@ -184,7 +199,8 @@ function buildKibanaUrl(urlConfig: UrlConfig, record: CustomUrlAnomalyRecordDoc) return `${resultPrefix}${resultQuery}${resultPostfix}`; } - ), + ); + }, replaceSingleTokenValues )(urlValue); } From 9aca58966d33017ee9a68fe65ec19cf0be9e9974 Mon Sep 17 00:00:00 2001 From: Marta Bondyra Date: Thu, 14 Nov 2019 12:22:39 +0100 Subject: [PATCH 6/9] feat: replace autocomplete for exists operator from ':*' to ': *' (#50293) --- .../public/autocomplete_providers/__tests__/operator.js | 2 +- .../public/autocomplete_providers/operator.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/__tests__/operator.js b/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/__tests__/operator.js index bb20e927039c0..0c033141128de 100644 --- a/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/__tests__/operator.js +++ b/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/__tests__/operator.js @@ -31,7 +31,7 @@ describe('Kuery operator suggestions', function () { const fieldName = 'custom_user_field'; const suggestions = getSuggestions({ fieldName }); expect(suggestions.length).to.eql(1); - expect(suggestions[0].text).to.be(':* '); + expect(suggestions[0].text).to.be(': * '); }); it('should return equals for string fields', () => { diff --git a/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/operator.js b/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/operator.js index 3955fdfd9afe7..eebd17a731c64 100644 --- a/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/operator.js +++ b/x-pack/legacy/plugins/kuery_autocomplete/public/autocomplete_providers/operator.js @@ -102,7 +102,7 @@ const operators = { />), fieldTypes: ['number', 'date', 'ip'] }, - ':*': { + ': *': { description: ( Date: Thu, 14 Nov 2019 08:31:58 -0300 Subject: [PATCH 7/9] [ML] sets truncateText to true for the 'Latest timestamp' column (#50004) * sets truncateText to true for the 'Latest timestamp' column * Truncates the creation time at the analytics panel --- .../ml/public/overview/components/analytics_panel/table.tsx | 1 + .../public/overview/components/anomaly_detection_panel/table.tsx | 1 + 2 files changed, 2 insertions(+) diff --git a/x-pack/legacy/plugins/ml/public/overview/components/analytics_panel/table.tsx b/x-pack/legacy/plugins/ml/public/overview/components/analytics_panel/table.tsx index 787f0a467f44d..7ee9cff107db8 100644 --- a/x-pack/legacy/plugins/ml/public/overview/components/analytics_panel/table.tsx +++ b/x-pack/legacy/plugins/ml/public/overview/components/analytics_panel/table.tsx @@ -72,6 +72,7 @@ export const AnalyticsTable: FC = ({ items }) => { dataType: 'date', render: (time: number) => formatHumanReadableDateTimeSeconds(time), textOnly: true, + truncateText: true, sortable: true, width: '20%', }, diff --git a/x-pack/legacy/plugins/ml/public/overview/components/anomaly_detection_panel/table.tsx b/x-pack/legacy/plugins/ml/public/overview/components/anomaly_detection_panel/table.tsx index 883726980fa94..c61d5889e9243 100644 --- a/x-pack/legacy/plugins/ml/public/overview/components/anomaly_detection_panel/table.tsx +++ b/x-pack/legacy/plugins/ml/public/overview/components/anomaly_detection_panel/table.tsx @@ -144,6 +144,7 @@ export const AnomalyDetectionTable: FC = ({ items, jobsList, statsBarData dataType: 'date', render: (time: number) => formatHumanReadableDateTimeSeconds(time), textOnly: true, + truncateText: true, sortable: true, width: '20%', }, From b5a0d4b03dc1e52eb13fc2386942d0f897b7e494 Mon Sep 17 00:00:00 2001 From: Anton Dosov Date: Thu, 14 Nov 2019 13:08:50 +0100 Subject: [PATCH 8/9] Add test for implicitly fixed #45150 (#50284) #45150 appeared in 7.3 and disappeared in 7.4 --- .../functional/apps/discover/_shared_links.js | 132 +++++++++++++----- test/functional/services/browser.ts | 9 ++ 2 files changed, 105 insertions(+), 36 deletions(-) diff --git a/test/functional/apps/discover/_shared_links.js b/test/functional/apps/discover/_shared_links.js index f0d34207a87a2..0b2b4f14f126d 100644 --- a/test/functional/apps/discover/_shared_links.js +++ b/test/functional/apps/discover/_shared_links.js @@ -25,11 +25,12 @@ export default function ({ getService, getPageObjects }) { const esArchiver = getService('esArchiver'); const kibanaServer = getService('kibanaServer'); const PageObjects = getPageObjects(['common', 'discover', 'share', 'timePicker']); + const browser = getService('browser'); describe('shared links', function describeIndexTests() { let baseUrl; - before(async function () { + async function setup({ storeStateInSessionStorage }) { baseUrl = PageObjects.common.getHostPort(); log.debug('baseUrl = ' + baseUrl); // browsers don't show the ':port' if it's 80 or 443 so we have to @@ -47,9 +48,12 @@ export default function ({ getService, getPageObjects }) { log.debug('load kibana index with default index pattern'); await esArchiver.load('discover'); - await esArchiver.loadIfNeeded('logstash_functional'); + await kibanaServer.uiSettings.replace({ + 'state:storeInSessionStorage': storeStateInSessionStorage + }); + log.debug('discover'); await PageObjects.common.navigateToApp('discover'); @@ -60,47 +64,103 @@ export default function ({ getService, getPageObjects }) { await PageObjects.common.sleep(1000); await PageObjects.share.clickShareTopNavButton(); - }); - describe('permalink', function () { - it('should allow for copying the snapshot URL', async function () { - const expectedUrl = - baseUrl + - '/app/kibana?_t=1453775307251#' + - '/discover?_g=(refreshInterval:(pause:!t,value:0),time' + - ':(from:\'2015-09-19T06:31:44.000Z\',to:\'2015-09' + - '-23T18:31:44.000Z\'))&_a=(columns:!(_source),index:\'logstash-' + - '*\',interval:auto,query:(language:kuery,query:\'\')' + - ',sort:!(!(\'@timestamp\',desc)))'; - const actualUrl = await PageObjects.share.getSharedUrl(); - // strip the timestamp out of each URL - expect(actualUrl.replace(/_t=\d{13}/, '_t=TIMESTAMP')).to.be( - expectedUrl.replace(/_t=\d{13}/, '_t=TIMESTAMP') - ); + return async () => { + await kibanaServer.uiSettings.replace({ + 'state:storeInSessionStorage': undefined + }); + }; + } + + describe('shared links with state in query', async () => { + let teardown; + before(async function () { + teardown = await setup({ storeStateInSessionStorage: false }); + }); + + after(async function () { + await teardown(); }); - it('should allow for copying the snapshot URL as a short URL', async function () { - const re = new RegExp(baseUrl + '/goto/[0-9a-f]{32}$'); - await PageObjects.share.checkShortenUrl(); - await retry.try(async () => { + describe('permalink', function () { + it('should allow for copying the snapshot URL', async function () { + const expectedUrl = + baseUrl + + '/app/kibana?_t=1453775307251#' + + '/discover?_g=(refreshInterval:(pause:!t,value:0),time' + + ':(from:\'2015-09-19T06:31:44.000Z\',to:\'2015-09' + + '-23T18:31:44.000Z\'))&_a=(columns:!(_source),index:\'logstash-' + + '*\',interval:auto,query:(language:kuery,query:\'\')' + + ',sort:!(!(\'@timestamp\',desc)))'; + const actualUrl = await PageObjects.share.getSharedUrl(); + // strip the timestamp out of each URL + expect(actualUrl.replace(/_t=\d{13}/, '_t=TIMESTAMP')).to.be( + expectedUrl.replace(/_t=\d{13}/, '_t=TIMESTAMP') + ); + }); + + it('should allow for copying the snapshot URL as a short URL', async function () { + const re = new RegExp(baseUrl + '/goto/[0-9a-f]{32}$'); + await PageObjects.share.checkShortenUrl(); + await retry.try(async () => { + const actualUrl = await PageObjects.share.getSharedUrl(); + expect(actualUrl).to.match(re); + }); + }); + + it('should allow for copying the saved object URL', async function () { + const expectedUrl = + baseUrl + + '/app/kibana#' + + '/discover/ab12e3c0-f231-11e6-9486-733b1ac9221a' + + '?_g=(refreshInterval%3A(pause%3A!t%2Cvalue%3A0)' + + '%2Ctime%3A(from%3A\'2015-09-19T06%3A31%3A44.000Z\'%2C' + + 'to%3A\'2015-09-23T18%3A31%3A44.000Z\'))'; + await PageObjects.discover.loadSavedSearch('A Saved Search'); + await PageObjects.share.clickShareTopNavButton(); + await PageObjects.share.exportAsSavedObject(); const actualUrl = await PageObjects.share.getSharedUrl(); - expect(actualUrl).to.match(re); + expect(actualUrl).to.be(expectedUrl); }); }); + }); + + describe('shared links with state in sessionStorage', async () => { + let teardown; + before(async function () { + teardown = await setup({ storeStateInSessionStorage: true }); + }); - it('should allow for copying the saved object URL', async function () { - const expectedUrl = - baseUrl + - '/app/kibana#' + - '/discover/ab12e3c0-f231-11e6-9486-733b1ac9221a' + - '?_g=(refreshInterval%3A(pause%3A!t%2Cvalue%3A0)' + - '%2Ctime%3A(from%3A\'2015-09-19T06%3A31%3A44.000Z\'%2C' + - 'to%3A\'2015-09-23T18%3A31%3A44.000Z\'))'; - await PageObjects.discover.loadSavedSearch('A Saved Search'); - await PageObjects.share.clickShareTopNavButton(); - await PageObjects.share.exportAsSavedObject(); - const actualUrl = await PageObjects.share.getSharedUrl(); - expect(actualUrl).to.be(expectedUrl); + after(async function () { + await teardown(); + }); + + describe('permalink', function () { + it('should allow for copying the snapshot URL as a short URL and should open it', async function () { + const re = new RegExp(baseUrl + '/goto/[0-9a-f]{32}$'); + await PageObjects.share.checkShortenUrl(); + let actualUrl; + await retry.try(async () => { + actualUrl = await PageObjects.share.getSharedUrl(); + expect(actualUrl).to.match(re); + }); + + const actualTime = await PageObjects.timePicker.getTimeConfig(); + + await browser.clearSessionStorage(); + await browser.get(actualUrl, false); + await retry.waitFor( + 'shortUrl resolves and opens', + async () => { + const resolvedUrl = await browser.getCurrentUrl(); + expect(resolvedUrl).to.match(/discover/); + const resolvedTime = await PageObjects.timePicker.getTimeConfig(); + expect(resolvedTime.start).to.equal(actualTime.start); + expect(resolvedTime.end).to.equal(actualTime.end); + return true; + } + ); + }); }); }); }); diff --git a/test/functional/services/browser.ts b/test/functional/services/browser.ts index 97e02958f3787..a8ce4270d4205 100644 --- a/test/functional/services/browser.ts +++ b/test/functional/services/browser.ts @@ -429,6 +429,15 @@ export async function BrowserProvider({ getService }: FtrProviderContext) { ); } + /** + * Clears session storage for the focused window/frame. + * + * @return {Promise} + */ + public async clearSessionStorage(): Promise { + await driver.executeScript('return window.sessionStorage.clear();'); + } + /** * Closes the currently focused window. In most environments, after the window has been * closed, it is necessary to explicitly switch to whatever window is now focused. From 4f888196b740fddaeb5e71c904bc692ccd83e150 Mon Sep 17 00:00:00 2001 From: Peter Pisljar Date: Thu, 14 Nov 2019 07:34:20 -0500 Subject: [PATCH 9/9] remove angular from Vis (#50402) --- .../public/renderers/visualization.tsx | 4 +- .../public/discover/angular/discover.js | 3 +- .../kibana/public/discover/kibana_services.ts | 2 +- .../saved_visualizations/_saved_vis.js | 3 +- .../__tests__/region_map_visualization.js | 4 +- .../coordinate_maps_visualization.js | 4 +- .../public/__tests__/metric_vis.js | 3 +- .../public/__tests__/table_vis_controller.js | 4 +- .../public/agg_table/__tests__/agg_table.js | 4 +- .../agg_table/__tests__/agg_table_group.js | 4 +- .../__tests__/tag_cloud_visualization.js | 4 +- .../public/components/vis_editor.js | 5 +- .../public/__tests__/vega_visualization.js | 4 +- .../visualizations/public/index.ts | 1 - .../tabify/__tests__/_get_columns.js | 4 +- .../tabify/__tests__/_integration.js | 4 +- .../tabify/__tests__/_response_writer.js | 4 +- .../buckets/_terms_other_bucket_helper.js | 3 +- .../ui/public/vis/__tests__/_agg_config.js | 4 +- .../ui/public/vis/__tests__/_agg_configs.js | 4 +- src/legacy/ui/public/vis/__tests__/_vis.js | 4 +- src/legacy/ui/public/vis/index.d.ts | 2 +- src/legacy/ui/public/vis/index.js | 2 +- src/legacy/ui/public/vis/vis.d.ts | 2 - src/legacy/ui/public/vis/vis.js | 289 +++++++++--------- .../vis_types/__tests__/vislib_vis_legend.js | 4 +- .../__tests__/visualizations/pie_chart.js | 6 +- src/legacy/ui/public/visualize/loader/vis.js | 179 ++++++----- 28 files changed, 255 insertions(+), 305 deletions(-) diff --git a/src/legacy/core_plugins/interpreter/public/renderers/visualization.tsx b/src/legacy/core_plugins/interpreter/public/renderers/visualization.tsx index 9de6cdeaf5ec3..f15cdf23fe15b 100644 --- a/src/legacy/core_plugins/interpreter/public/renderers/visualization.tsx +++ b/src/legacy/core_plugins/interpreter/public/renderers/visualization.tsx @@ -21,7 +21,7 @@ import chrome from 'ui/chrome'; import React from 'react'; import { render, unmountComponentAtNode } from 'react-dom'; // @ts-ignore -import { VisProvider } from '../../../../ui/public/visualize/loader/vis'; +import { Vis } from '../../../../ui/public/visualize/loader/vis'; import { Visualization } from '../../../../ui/public/visualize/components'; export const visualization = () => ({ @@ -33,8 +33,6 @@ export const visualization = () => ({ const visType = config.visType || visConfig.type; const $injector = await chrome.dangerouslyGetActiveInjector(); const $rootScope = $injector.get('$rootScope') as any; - const Private = $injector.get('Private') as any; - const Vis = Private(VisProvider); if (handlers.vis) { // special case in visualize, we need to render first (without executing the expression), for maps to work diff --git a/src/legacy/core_plugins/kibana/public/discover/angular/discover.js b/src/legacy/core_plugins/kibana/public/discover/angular/discover.js index ed5049aa912e0..3a3f58ca83af0 100644 --- a/src/legacy/core_plugins/kibana/public/discover/angular/discover.js +++ b/src/legacy/core_plugins/kibana/public/discover/angular/discover.js @@ -57,7 +57,7 @@ import { subscribeWithScope, tabifyAggResponse, vislibSeriesResponseHandlerProvider, - VisProvider, + Vis, SavedObjectSaveModal, } from '../kibana_services'; @@ -190,7 +190,6 @@ function discoverController( localStorage, uiCapabilities ) { - const Vis = Private(VisProvider); const responseHandler = vislibSeriesResponseHandlerProvider().handler; const getUnhashableStates = Private(getUnhashableStatesProvider); const shareContextMenuExtensions = Private(ShareContextMenuExtensionsRegistryProvider); diff --git a/src/legacy/core_plugins/kibana/public/discover/kibana_services.ts b/src/legacy/core_plugins/kibana/public/discover/kibana_services.ts index b78d05e68acad..a220cf59f6cf6 100644 --- a/src/legacy/core_plugins/kibana/public/discover/kibana_services.ts +++ b/src/legacy/core_plugins/kibana/public/discover/kibana_services.ts @@ -114,7 +114,7 @@ export { tabifyAggResponse } from 'ui/agg_response/tabify'; export { vislibSeriesResponseHandlerProvider } from 'ui/vis/response_handlers/vislib'; // EXPORT types -export { VisProvider } from 'ui/vis'; +export { Vis } from 'ui/vis'; export { StaticIndexPattern, IndexPatterns, IndexPattern, FieldType } from 'ui/index_patterns'; export { SearchSource } from 'ui/courier'; export { ElasticSearchHit } from 'ui/registry/doc_views_types'; diff --git a/src/legacy/core_plugins/kibana/public/visualize/saved_visualizations/_saved_vis.js b/src/legacy/core_plugins/kibana/public/visualize/saved_visualizations/_saved_vis.js index f8adaed0bf584..aec80b8d13551 100644 --- a/src/legacy/core_plugins/kibana/public/visualize/saved_visualizations/_saved_vis.js +++ b/src/legacy/core_plugins/kibana/public/visualize/saved_visualizations/_saved_vis.js @@ -25,7 +25,7 @@ * NOTE: It's a type of SavedObject, but specific to visualizations. */ -import { VisProvider } from 'ui/vis'; +import { Vis } from 'ui/vis'; import { uiModules } from 'ui/modules'; import { updateOldState } from 'ui/vis/vis_update_state'; import { VisualizeConstants } from '../visualize_constants'; @@ -39,7 +39,6 @@ import { uiModules .get('app/visualize') .factory('SavedVis', function (Promise, savedSearches, Private) { - const Vis = Private(VisProvider); const SavedObject = Private(SavedObjectProvider); createLegacyClass(SavedVis).inherits(SavedObject); function SavedVis(opts) { diff --git a/src/legacy/core_plugins/region_map/public/__tests__/region_map_visualization.js b/src/legacy/core_plugins/region_map/public/__tests__/region_map_visualization.js index 9bfa413257967..b57fbd637f0b7 100644 --- a/src/legacy/core_plugins/region_map/public/__tests__/region_map_visualization.js +++ b/src/legacy/core_plugins/region_map/public/__tests__/region_map_visualization.js @@ -22,7 +22,7 @@ import ngMock from 'ng_mock'; import _ from 'lodash'; import ChoroplethLayer from '../choropleth_layer'; import LogstashIndexPatternStubProvider from 'fixtures/stubbed_logstash_index_pattern'; -import * as visModule from 'ui/vis'; +import { Vis } from 'ui/vis'; import { ImageComparator } from 'test_utils/image_comparator'; import worldJson from './world.json'; import EMS_CATALOGUE from '../../../../ui/public/vis/__tests__/map/ems_mocks/sample_manifest.json'; @@ -50,7 +50,6 @@ const PIXEL_DIFF = 96; describe('RegionMapsVisualizationTests', function () { let domNode; let RegionMapsVisualization; - let Vis; let indexPattern; let vis; let dependencies; @@ -113,7 +112,6 @@ describe('RegionMapsVisualizationTests', function () { visualizationsSetup.types.registerVisualization(() => createRegionMapTypeDefinition(dependencies)); } - Vis = Private(visModule.VisProvider); RegionMapsVisualization = createRegionMapVisualization(dependencies); indexPattern = Private(LogstashIndexPatternStubProvider); diff --git a/src/legacy/core_plugins/tile_map/public/__tests__/coordinate_maps_visualization.js b/src/legacy/core_plugins/tile_map/public/__tests__/coordinate_maps_visualization.js index 751f92fe88215..0e3c4fdd9d355 100644 --- a/src/legacy/core_plugins/tile_map/public/__tests__/coordinate_maps_visualization.js +++ b/src/legacy/core_plugins/tile_map/public/__tests__/coordinate_maps_visualization.js @@ -20,7 +20,7 @@ import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import LogstashIndexPatternStubProvider from 'fixtures/stubbed_logstash_index_pattern'; -import * as visModule from 'ui/vis'; +import { Vis } from 'ui/vis'; import { ImageComparator } from 'test_utils/image_comparator'; import dummyESResponse from './dummy_es_response.json'; import initial from './initial.png'; @@ -65,7 +65,6 @@ let visRegComplete = false; describe('CoordinateMapsVisualizationTest', function () { let domNode; let CoordinateMapsVisualization; - let Vis; let indexPattern; let vis; let dependencies; @@ -91,7 +90,6 @@ describe('CoordinateMapsVisualizationTest', function () { } - Vis = Private(visModule.VisProvider); CoordinateMapsVisualization = createTileMapVisualization(dependencies); indexPattern = Private(LogstashIndexPatternStubProvider); diff --git a/src/legacy/core_plugins/vis_type_metric/public/__tests__/metric_vis.js b/src/legacy/core_plugins/vis_type_metric/public/__tests__/metric_vis.js index 7f626df6a4ea3..384beb3764e2e 100644 --- a/src/legacy/core_plugins/vis_type_metric/public/__tests__/metric_vis.js +++ b/src/legacy/core_plugins/vis_type_metric/public/__tests__/metric_vis.js @@ -21,7 +21,7 @@ import $ from 'jquery'; import ngMock from 'ng_mock'; import expect from '@kbn/expect'; -import { VisProvider } from 'ui/vis'; +import { Vis } from 'ui/vis'; import LogstashIndexPatternStubProvider from 'fixtures/stubbed_logstash_index_pattern'; import { createMetricVisTypeDefinition } from '../metric_vis_type'; @@ -34,7 +34,6 @@ describe('metric_vis - createMetricVisTypeDefinition', () => { beforeEach( ngMock.inject(Private => { setup = () => { - const Vis = Private(VisProvider); const metricVisType = createMetricVisTypeDefinition(); const indexPattern = Private(LogstashIndexPatternStubProvider); diff --git a/src/legacy/core_plugins/vis_type_table/public/__tests__/table_vis_controller.js b/src/legacy/core_plugins/vis_type_table/public/__tests__/table_vis_controller.js index abebf8190dc9f..4153ce2da36a7 100644 --- a/src/legacy/core_plugins/vis_type_table/public/__tests__/table_vis_controller.js +++ b/src/legacy/core_plugins/vis_type_table/public/__tests__/table_vis_controller.js @@ -21,7 +21,7 @@ import $ from 'jquery'; import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { legacyResponseHandlerProvider } from 'ui/vis/response_handlers/legacy'; -import { VisProvider } from 'ui/vis'; +import { Vis } from 'ui/vis'; import { VisFactoryProvider } from 'ui/vis/vis_factory'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; import { AppStateProvider } from 'ui/state_management/app_state'; @@ -36,7 +36,6 @@ describe('Table Vis - Controller', async function () { let Private; let $scope; let $el; - let Vis; let fixtures; let AppState; let tableAggResponse; @@ -63,7 +62,6 @@ describe('Table Vis - Controller', async function () { $compile = $injector.get('$compile'); fixtures = require('fixtures/fake_hierarchical_data'); AppState = Private(AppStateProvider); - Vis = Private(VisProvider); tableAggResponse = legacyResponseHandlerProvider().handler; }) ); diff --git a/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table.js b/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table.js index d22ff92c4d3f6..13e8a4fd9535a 100644 --- a/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table.js +++ b/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table.js @@ -25,7 +25,7 @@ import fixtures from 'fixtures/fake_hierarchical_data'; import sinon from 'sinon'; import { legacyResponseHandlerProvider } from 'ui/vis/response_handlers/legacy'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; -import { VisProvider } from 'ui/vis'; +import { Vis } from 'ui/vis'; import { tabifyAggResponse } from 'ui/agg_response/tabify'; import { round } from 'lodash'; @@ -36,7 +36,6 @@ import { setup as visualizationsSetup } from '../../../../visualizations/public/ describe('Table Vis - AggTable Directive', function () { let $rootScope; let $compile; - let Vis; let indexPattern; let settings; let tableAggResponse; @@ -113,7 +112,6 @@ describe('Table Vis - AggTable Directive', function () { ngMock.inject(function ($injector, Private, config) { tableAggResponse = legacyResponseHandlerProvider().handler; indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); - Vis = Private(VisProvider); settings = config; $rootScope = $injector.get('$rootScope'); diff --git a/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table_group.js b/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table_group.js index e8359e37d6186..f4e3a8e36605c 100644 --- a/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table_group.js +++ b/src/legacy/core_plugins/vis_type_table/public/agg_table/__tests__/agg_table_group.js @@ -23,13 +23,12 @@ import expect from '@kbn/expect'; import fixtures from 'fixtures/fake_hierarchical_data'; import { legacyResponseHandlerProvider } from 'ui/vis/response_handlers/legacy'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; -import { VisProvider } from 'ui/vis'; +import { Vis } from 'ui/vis'; import { tabifyAggResponse } from 'ui/agg_response/tabify'; describe('Table Vis - AggTableGroup Directive', function () { let $rootScope; let $compile; - let Vis; let indexPattern; let tableAggResponse; const tabifiedData = {}; @@ -69,7 +68,6 @@ describe('Table Vis - AggTableGroup Directive', function () { tableAggResponse = legacyResponseHandlerProvider().handler; indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); - Vis = Private(VisProvider); $rootScope = $injector.get('$rootScope'); $compile = $injector.get('$compile'); diff --git a/src/legacy/core_plugins/vis_type_tagcloud/public/components/__tests__/tag_cloud_visualization.js b/src/legacy/core_plugins/vis_type_tagcloud/public/components/__tests__/tag_cloud_visualization.js index 69d08d8cb3f74..0cb903faac47c 100644 --- a/src/legacy/core_plugins/vis_type_tagcloud/public/components/__tests__/tag_cloud_visualization.js +++ b/src/legacy/core_plugins/vis_type_tagcloud/public/components/__tests__/tag_cloud_visualization.js @@ -20,7 +20,7 @@ import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import LogstashIndexPatternStubProvider from 'fixtures/stubbed_logstash_index_pattern'; -import * as visModule from 'ui/vis'; +import { Vis } from 'ui/vis'; import { ImageComparator } from 'test_utils/image_comparator'; import { TagCloudVisualization } from '../tag_cloud_visualization'; import basicdrawPng from './basicdraw.png'; @@ -33,7 +33,6 @@ const PIXEL_DIFF = 64; describe('TagCloudVisualizationTest', function () { let domNode; - let Vis; let indexPattern; let vis; let imageComparator; @@ -57,7 +56,6 @@ describe('TagCloudVisualizationTest', function () { beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject((Private) => { - Vis = Private(visModule.VisProvider); indexPattern = Private(LogstashIndexPatternStubProvider); })); diff --git a/src/legacy/core_plugins/vis_type_timeseries/public/components/vis_editor.js b/src/legacy/core_plugins/vis_type_timeseries/public/components/vis_editor.js index 842d3aa6c4ad7..2b42c22ad7c43 100644 --- a/src/legacy/core_plugins/vis_type_timeseries/public/components/vis_editor.js +++ b/src/legacy/core_plugins/vis_type_timeseries/public/components/vis_editor.js @@ -44,8 +44,7 @@ const APP_NAME = 'VisEditor'; export class VisEditor extends Component { constructor(props) { super(props); - const { vis } = props; - this.appState = vis.API.getAppState(); + this.appState = props.appState; this.localStorage = new Storage(window.localStorage); this.state = { model: props.visParams, @@ -183,7 +182,6 @@ export class VisEditor extends Component { dirty={this.state.dirty} autoApply={this.state.autoApply} model={model} - appState={this.appState} savedObj={this.props.savedObj} timeRange={this.props.timeRange} uiState={this.uiState} @@ -239,4 +237,5 @@ VisEditor.propTypes = { isEditorMode: PropTypes.bool, savedObj: PropTypes.object, timeRange: PropTypes.object, + appState: PropTypes.object, }; diff --git a/src/legacy/core_plugins/vis_type_vega/public/__tests__/vega_visualization.js b/src/legacy/core_plugins/vis_type_vega/public/__tests__/vega_visualization.js index 46725a2c5d01f..191f35d2e03ea 100644 --- a/src/legacy/core_plugins/vis_type_vega/public/__tests__/vega_visualization.js +++ b/src/legacy/core_plugins/vis_type_vega/public/__tests__/vega_visualization.js @@ -23,7 +23,7 @@ import ngMock from 'ng_mock'; import $ from 'jquery'; import { createVegaVisualization } from '../vega_visualization'; import LogstashIndexPatternStubProvider from 'fixtures/stubbed_logstash_index_pattern'; -import * as visModule from 'ui/vis'; +import { Vis } from 'ui/vis'; import { ImageComparator } from 'test_utils/image_comparator'; import vegaliteGraph from '!!raw-loader!./vegalite_graph.hjson'; @@ -50,7 +50,6 @@ const PIXEL_DIFF = 30; describe('VegaVisualizations', () => { let domNode; let VegaVisualization; - let Vis; let indexPattern; let vis; let imageComparator; @@ -73,7 +72,6 @@ describe('VegaVisualizations', () => { ); } - Vis = Private(visModule.VisProvider); VegaVisualization = createVegaVisualization(vegaVisualizationDependencies); indexPattern = Private(LogstashIndexPatternStubProvider); diff --git a/src/legacy/core_plugins/visualizations/public/index.ts b/src/legacy/core_plugins/visualizations/public/index.ts index ad86c9ddb14c5..ca79f547890f9 100644 --- a/src/legacy/core_plugins/visualizations/public/index.ts +++ b/src/legacy/core_plugins/visualizations/public/index.ts @@ -39,7 +39,6 @@ export { DefaultEditorSize } from 'ui/vis/editor_size'; import * as types from 'ui/vis/vis'; export type Vis = types.Vis; export type VisParams = types.VisParams; -export type VisProvider = types.VisProvider; export type VisState = types.VisState; export { VisualizationController } from 'ui/vis/vis_types/vis_type'; export { Status } from 'ui/vis/update_status'; diff --git a/src/legacy/ui/public/agg_response/tabify/__tests__/_get_columns.js b/src/legacy/ui/public/agg_response/tabify/__tests__/_get_columns.js index 27b390ed7e471..39303e94adc6f 100644 --- a/src/legacy/ui/public/agg_response/tabify/__tests__/_get_columns.js +++ b/src/legacy/ui/public/agg_response/tabify/__tests__/_get_columns.js @@ -20,15 +20,13 @@ import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { tabifyGetColumns } from '../_get_columns'; -import { VisProvider } from '../../../vis'; +import { Vis } from '../../../vis'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; describe('get columns', function () { - let Vis; let indexPattern; beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private) { - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/agg_response/tabify/__tests__/_integration.js b/src/legacy/ui/public/agg_response/tabify/__tests__/_integration.js index fd8df904b600f..dabd66a22fcd2 100644 --- a/src/legacy/ui/public/agg_response/tabify/__tests__/_integration.js +++ b/src/legacy/ui/public/agg_response/tabify/__tests__/_integration.js @@ -22,16 +22,14 @@ import fixtures from 'fixtures/fake_hierarchical_data'; import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { tabifyAggResponse } from '../tabify'; -import { VisProvider } from '../../../vis'; +import { Vis } from '../../../vis'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; describe('tabifyAggResponse Integration', function () { - let Vis; let indexPattern; beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private) { - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/agg_response/tabify/__tests__/_response_writer.js b/src/legacy/ui/public/agg_response/tabify/__tests__/_response_writer.js index 09668c638d695..001132f97c95a 100644 --- a/src/legacy/ui/public/agg_response/tabify/__tests__/_response_writer.js +++ b/src/legacy/ui/public/agg_response/tabify/__tests__/_response_writer.js @@ -20,11 +20,10 @@ import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { TabbedAggResponseWriter } from '../_response_writer'; -import { VisProvider } from '../../../vis'; +import { Vis } from '../../../vis'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; describe('TabbedAggResponseWriter class', function () { - let Vis; let Private; let indexPattern; @@ -32,7 +31,6 @@ describe('TabbedAggResponseWriter class', function () { beforeEach(ngMock.inject(function ($injector) { Private = $injector.get('Private'); - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/agg_types/__tests__/buckets/_terms_other_bucket_helper.js b/src/legacy/ui/public/agg_types/__tests__/buckets/_terms_other_bucket_helper.js index dcadeacb3d1fe..759a6b80d8faf 100644 --- a/src/legacy/ui/public/agg_types/__tests__/buckets/_terms_other_bucket_helper.js +++ b/src/legacy/ui/public/agg_types/__tests__/buckets/_terms_other_bucket_helper.js @@ -20,7 +20,7 @@ import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { buildOtherBucketAgg, mergeOtherBucketAggResponse, updateMissingBucket } from '../../buckets/_terms_other_bucket_helper'; -import { VisProvider } from '../../../vis'; +import { Vis } from '../../../vis'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; const visConfigSingleTerm = { @@ -158,7 +158,6 @@ describe('Terms Agg Other bucket helper', () => { function init(aggConfig) { ngMock.module('kibana'); ngMock.inject((Private) => { - const Vis = Private(VisProvider); const indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); vis = new Vis(indexPattern, aggConfig); diff --git a/src/legacy/ui/public/vis/__tests__/_agg_config.js b/src/legacy/ui/public/vis/__tests__/_agg_config.js index 46d7ed4601f29..2e2e0c31bdb8a 100644 --- a/src/legacy/ui/public/vis/__tests__/_agg_config.js +++ b/src/legacy/ui/public/vis/__tests__/_agg_config.js @@ -20,7 +20,7 @@ import sinon from 'sinon'; import expect from '@kbn/expect'; import ngMock from 'ng_mock'; -import { VisProvider } from '..'; +import { Vis } from '..'; import { AggType } from '../../agg_types/agg_type'; import { AggConfig } from '../../agg_types/agg_config'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; @@ -28,12 +28,10 @@ import { fieldFormats } from '../../registry/field_formats'; describe('AggConfig', function () { - let Vis; let indexPattern; beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private) { - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/vis/__tests__/_agg_configs.js b/src/legacy/ui/public/vis/__tests__/_agg_configs.js index 96e4aa943ed1d..3240bd56f1502 100644 --- a/src/legacy/ui/public/vis/__tests__/_agg_configs.js +++ b/src/legacy/ui/public/vis/__tests__/_agg_configs.js @@ -22,7 +22,7 @@ import sinon from 'sinon'; import expect from '@kbn/expect'; import ngMock from 'ng_mock'; import { AggConfig } from '../../agg_types/agg_config'; -import { VisProvider } from '..'; +import { Vis } from '..'; import { AggConfigs } from '../../agg_types/agg_configs'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; import { Schemas } from '../editors/default/schemas'; @@ -30,13 +30,11 @@ import { AggGroupNames } from '../editors/default/agg_groups'; describe('AggConfigs', function () { - let Vis; let indexPattern; beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private) { // load main deps - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/vis/__tests__/_vis.js b/src/legacy/ui/public/vis/__tests__/_vis.js index 5a2f93ab35b50..1d5e2de6dafe3 100644 --- a/src/legacy/ui/public/vis/__tests__/_vis.js +++ b/src/legacy/ui/public/vis/__tests__/_vis.js @@ -20,13 +20,12 @@ import _ from 'lodash'; import ngMock from 'ng_mock'; import expect from '@kbn/expect'; -import { VisProvider } from '..'; +import { Vis } from '..'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; import { start as visualizations } from '../../../../core_plugins/visualizations/public/np_ready/public/legacy'; describe('Vis Class', function () { let indexPattern; - let Vis; let visTypes; let vis; @@ -43,7 +42,6 @@ describe('Vis Class', function () { beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private) { - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); visTypes = visualizations.types; })); diff --git a/src/legacy/ui/public/vis/index.d.ts b/src/legacy/ui/public/vis/index.d.ts index 5a2a7edb6329a..791ce2563e0f1 100644 --- a/src/legacy/ui/public/vis/index.d.ts +++ b/src/legacy/ui/public/vis/index.d.ts @@ -18,5 +18,5 @@ */ export { AggConfig } from '../agg_types/agg_config'; -export { Vis, VisProvider, VisParams, VisState } from './vis'; +export { Vis, VisParams, VisState } from './vis'; export { VisualizationController, VisType } from './vis_types/vis_type'; diff --git a/src/legacy/ui/public/vis/index.js b/src/legacy/ui/public/vis/index.js index 711b465a1e8a5..05cd030f7d100 100644 --- a/src/legacy/ui/public/vis/index.js +++ b/src/legacy/ui/public/vis/index.js @@ -17,4 +17,4 @@ * under the License. */ -export { VisProvider } from './vis'; +export { Vis } from './vis'; diff --git a/src/legacy/ui/public/vis/vis.d.ts b/src/legacy/ui/public/vis/vis.d.ts index be73cccf06a59..e16562641801e 100644 --- a/src/legacy/ui/public/vis/vis.d.ts +++ b/src/legacy/ui/public/vis/vis.d.ts @@ -30,8 +30,6 @@ export interface Vis { [key: string]: any; } -export type VisProvider = (...dependencies: any[]) => Vis; - export interface VisParams { [key: string]: any; } diff --git a/src/legacy/ui/public/vis/vis.js b/src/legacy/ui/public/vis/vis.js index c1fff1556e3ad..304289a5cfa07 100644 --- a/src/legacy/ui/public/vis/vis.js +++ b/src/legacy/ui/public/vis/vis.js @@ -38,181 +38,178 @@ import { start as visualizations } from '../../../core_plugins/visualizations/pu import '../directives/bind'; -export function VisProvider(Private, getAppState) { - const visTypes = visualizations.types; - - class Vis extends EventEmitter { - constructor(indexPattern, visState) { - super(); - visState = visState || {}; - - if (_.isString(visState)) { - visState = { - type: visState - }; - } - this.indexPattern = indexPattern; - this._setUiState(new PersistedState()); - this.setCurrentState(visState); - this.setState(this.getCurrentState(), false); - - // Session state is for storing information that is transitory, and will not be saved with the visualization. - // For instance, map bounds, which depends on the view port, browser window size, etc. - this.sessionState = {}; - - this.API = { - SearchSource: SearchSource, - events: { - filter: data => this.eventsSubject.next({ name: 'filterBucket', data }), - brush: data => this.eventsSubject.next({ name: 'brush', data }), - }, - getAppState, +const visTypes = visualizations.types; + +class Vis extends EventEmitter { + constructor(indexPattern, visState) { + super(); + visState = visState || {}; + + if (_.isString(visState)) { + visState = { + type: visState }; } + this.indexPattern = indexPattern; + this._setUiState(new PersistedState()); + this.setCurrentState(visState); + this.setState(this.getCurrentState(), false); + + // Session state is for storing information that is transitory, and will not be saved with the visualization. + // For instance, map bounds, which depends on the view port, browser window size, etc. + this.sessionState = {}; + + this.API = { + SearchSource: SearchSource, + events: { + filter: data => this.eventsSubject.next({ name: 'filterBucket', data }), + brush: data => this.eventsSubject.next({ name: 'brush', data }), + }, + }; + } - setCurrentState(state) { - this.title = state.title || ''; - const type = state.type || this.type; - if (_.isString(type)) { - this.type = visTypes.get(type); - if (!this.type) { - throw new Error(`Invalid type "${type}"`); - } - } else { - this.type = type; + setCurrentState(state) { + this.title = state.title || ''; + const type = state.type || this.type; + if (_.isString(type)) { + this.type = visTypes.get(type); + if (!this.type) { + throw new Error(`Invalid type "${type}"`); } + } else { + this.type = type; + } - this.params = _.defaults({}, - _.cloneDeep(state.params || {}), - _.cloneDeep(this.type.visConfig.defaults || {}) - ); + this.params = _.defaults({}, + _.cloneDeep(state.params || {}), + _.cloneDeep(this.type.visConfig.defaults || {}) + ); - updateVisualizationConfig(state.params, this.params); + updateVisualizationConfig(state.params, this.params); - if (state.aggs || !this.aggs) { - this.aggs = new AggConfigs(this.indexPattern, state.aggs ? state.aggs.aggs || state.aggs : [], this.type.schemas.all); - } + if (state.aggs || !this.aggs) { + this.aggs = new AggConfigs(this.indexPattern, state.aggs ? state.aggs.aggs || state.aggs : [], this.type.schemas.all); } + } - setState(state, updateCurrentState = true) { - this._state = _.cloneDeep(state); - if (updateCurrentState) { - this.setCurrentState(this._state); - } + setState(state, updateCurrentState = true) { + this._state = _.cloneDeep(state); + if (updateCurrentState) { + this.setCurrentState(this._state); } + } - updateState() { - this.setState(this.getCurrentState(true)); - this.emit('update'); - } + updateState() { + this.setState(this.getCurrentState(true)); + this.emit('update'); + } - forceReload() { - this.emit('reload'); - } + forceReload() { + this.emit('reload'); + } - getCurrentState(includeDisabled) { - return { - title: this.title, - type: this.type.name, - params: _.cloneDeep(this.params), - aggs: this.aggs.aggs - .map(agg => agg.toJSON()) - .filter(agg => includeDisabled || agg.enabled) - .filter(Boolean) - }; - } + getCurrentState(includeDisabled) { + return { + title: this.title, + type: this.type.name, + params: _.cloneDeep(this.params), + aggs: this.aggs.aggs + .map(agg => agg.toJSON()) + .filter(agg => includeDisabled || agg.enabled) + .filter(Boolean) + }; + } - getSerializableState(state) { - return { - title: state.title, - type: state.type, - params: _.cloneDeep(state.params), - aggs: state.aggs.aggs - .map(agg => agg.toJSON()) - .filter(agg => agg.enabled) - .filter(Boolean) - }; - } + getSerializableState(state) { + return { + title: state.title, + type: state.type, + params: _.cloneDeep(state.params), + aggs: state.aggs.aggs + .map(agg => agg.toJSON()) + .filter(agg => agg.enabled) + .filter(Boolean) + }; + } - copyCurrentState(includeDisabled = false) { - const state = this.getCurrentState(includeDisabled); - state.aggs = new AggConfigs(this.indexPattern, state.aggs.aggs || state.aggs, this.type.schemas.all); - return state; - } + copyCurrentState(includeDisabled = false) { + const state = this.getCurrentState(includeDisabled); + state.aggs = new AggConfigs(this.indexPattern, state.aggs.aggs || state.aggs, this.type.schemas.all); + return state; + } - getStateInternal(includeDisabled) { - return { - title: this._state.title, - type: this._state.type, - params: this._state.params, - aggs: this._state.aggs - .filter(agg => includeDisabled || agg.enabled) - }; - } + getStateInternal(includeDisabled) { + return { + title: this._state.title, + type: this._state.type, + params: this._state.params, + aggs: this._state.aggs + .filter(agg => includeDisabled || agg.enabled) + }; + } - getEnabledState() { - return this.getStateInternal(false); - } + getEnabledState() { + return this.getStateInternal(false); + } - getAggConfig() { - return this.aggs.clone({ enabledOnly: true }); - } + getAggConfig() { + return this.aggs.clone({ enabledOnly: true }); + } - getState() { - return this.getStateInternal(true); - } + getState() { + return this.getStateInternal(true); + } - isHierarchical() { - if (_.isFunction(this.type.hierarchicalData)) { - return !!this.type.hierarchicalData(this); - } else { - return !!this.type.hierarchicalData; - } + isHierarchical() { + if (_.isFunction(this.type.hierarchicalData)) { + return !!this.type.hierarchicalData(this); + } else { + return !!this.type.hierarchicalData; } + } - hasSchemaAgg(schemaName, aggTypeName) { - const aggs = this.aggs.bySchemaName(schemaName) || []; - return aggs.some(function (agg) { - if (!agg.type || !agg.type.name) return false; - return agg.type.name === aggTypeName; - }); - } + hasSchemaAgg(schemaName, aggTypeName) { + const aggs = this.aggs.bySchemaName(schemaName) || []; + return aggs.some(function (agg) { + if (!agg.type || !agg.type.name) return false; + return agg.type.name === aggTypeName; + }); + } - hasUiState() { - return !!this.__uiState; - } + hasUiState() { + return !!this.__uiState; + } - /*** - * this should not be used outside of visualize - * @param uiState - * @private - */ - _setUiState(uiState) { - if (uiState instanceof PersistedState) { - this.__uiState = uiState; - } + /*** + * this should not be used outside of visualize + * @param uiState + * @private + */ + _setUiState(uiState) { + if (uiState instanceof PersistedState) { + this.__uiState = uiState; } + } - getUiState() { - return this.__uiState; - } + getUiState() { + return this.__uiState; + } - /** - * Currently this is only used to extract map-specific information - * (e.g. mapZoom, mapCenter). - */ - uiStateVal(key, val) { - if (this.hasUiState()) { - if (_.isUndefined(val)) { - return this.__uiState.get(key); - } - return this.__uiState.set(key, val); + /** + * Currently this is only used to extract map-specific information + * (e.g. mapZoom, mapCenter). + */ + uiStateVal(key, val) { + if (this.hasUiState()) { + if (_.isUndefined(val)) { + return this.__uiState.get(key); } - return val; + return this.__uiState.set(key, val); } + return val; } +} - Vis.prototype.type = 'histogram'; +Vis.prototype.type = 'histogram'; - return Vis; -} +export { Vis }; diff --git a/src/legacy/ui/public/vis/vis_types/__tests__/vislib_vis_legend.js b/src/legacy/ui/public/vis/vis_types/__tests__/vislib_vis_legend.js index 18eef99f05a75..afb3fea15a430 100644 --- a/src/legacy/ui/public/vis/vis_types/__tests__/vislib_vis_legend.js +++ b/src/legacy/ui/public/vis/vis_types/__tests__/vislib_vis_legend.js @@ -21,7 +21,7 @@ import $ from 'jquery'; import _ from 'lodash'; import expect from '@kbn/expect'; import ngMock from 'ng_mock'; -import { VisProvider } from '../../vis'; +import { Vis } from '../../vis'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; describe('visualize_legend directive', function () { @@ -29,7 +29,6 @@ describe('visualize_legend directive', function () { let $compile; let $timeout; let $el; - let Vis; let indexPattern; let fixtures; @@ -39,7 +38,6 @@ describe('visualize_legend directive', function () { $compile = $injector.get('$compile'); $timeout = $injector.get('$timeout'); fixtures = require('fixtures/fake_hierarchical_data'); - Vis = Private(VisProvider); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); })); diff --git a/src/legacy/ui/public/vislib/__tests__/visualizations/pie_chart.js b/src/legacy/ui/public/vislib/__tests__/visualizations/pie_chart.js index a4f62e6ceb431..5692ae65af281 100644 --- a/src/legacy/ui/public/vislib/__tests__/visualizations/pie_chart.js +++ b/src/legacy/ui/public/vislib/__tests__/visualizations/pie_chart.js @@ -24,7 +24,7 @@ import _ from 'lodash'; import fixtures from 'fixtures/fake_hierarchical_data'; import $ from 'jquery'; import FixturesVislibVisFixtureProvider from 'fixtures/vislib/_vis_fixture'; -import { VisProvider } from '../../../vis'; +import { Vis } from '../../../vis'; import '../../../persisted_state'; import FixturesStubbedLogstashIndexPatternProvider from 'fixtures/stubbed_logstash_index_pattern'; import { vislibSlicesResponseHandlerProvider } from '../../../vis/response_handlers/vislib'; @@ -113,7 +113,6 @@ describe('No global chart settings', function () { addTooltip: true }; let chart1; - let Vis; let persistedState; let indexPattern; let responseHandler; @@ -123,7 +122,6 @@ describe('No global chart settings', function () { beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private, $injector) { chart1 = Private(FixturesVislibVisFixtureProvider)(visLibParams1); - Vis = Private(VisProvider); persistedState = new ($injector.get('PersistedState'))(); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); responseHandler = vislibSlicesResponseHandlerProvider().handler; @@ -203,7 +201,6 @@ describe('Vislib PieChart Class Test Suite', function () { addTooltip: true }; let vis; - let Vis; let persistedState; let indexPattern; let data; @@ -213,7 +210,6 @@ describe('Vislib PieChart Class Test Suite', function () { beforeEach(ngMock.module('kibana')); beforeEach(ngMock.inject(function (Private, $injector) { vis = Private(FixturesVislibVisFixtureProvider)(visLibParams); - Vis = Private(VisProvider); persistedState = new ($injector.get('PersistedState'))(); indexPattern = Private(FixturesStubbedLogstashIndexPatternProvider); responseHandler = vislibSlicesResponseHandlerProvider().handler; diff --git a/src/legacy/ui/public/visualize/loader/vis.js b/src/legacy/ui/public/visualize/loader/vis.js index 1942fd58afebb..29208563055d0 100644 --- a/src/legacy/ui/public/visualize/loader/vis.js +++ b/src/legacy/ui/public/visualize/loader/vis.js @@ -33,114 +33,109 @@ import { PersistedState } from '../../persisted_state'; import { start as visualizations } from '../../../../core_plugins/visualizations/public/np_ready/public/legacy'; -export function VisProvider(getAppState) { - const visTypes = visualizations.types; - - class Vis extends EventEmitter { - constructor(visState = { type: 'histogram' }) { - super(); - - this._setUiState(new PersistedState()); - this.setState(visState); - - // Session state is for storing information that is transitory, and will not be saved with the visualization. - // For instance, map bounds, which depends on the view port, browser window size, etc. - this.sessionState = {}; - - this.API = { - events: { - filter: data => { - if (!this.eventsSubject) return; - this.eventsSubject.next({ name: 'filterBucket', data }); - }, - brush: data => { - if (!this.eventsSubject) return; - this.eventsSubject.next({ name: 'brush', data }); - }, +const visTypes = visualizations.types; + +export class Vis extends EventEmitter { + constructor(visState = { type: 'histogram' }) { + super(); + + this._setUiState(new PersistedState()); + this.setState(visState); + + // Session state is for storing information that is transitory, and will not be saved with the visualization. + // For instance, map bounds, which depends on the view port, browser window size, etc. + this.sessionState = {}; + + this.API = { + events: { + filter: data => { + if (!this.eventsSubject) return; + this.eventsSubject.next({ name: 'filterBucket', data }); }, - getAppState, - }; - } + brush: data => { + if (!this.eventsSubject) return; + this.eventsSubject.next({ name: 'brush', data }); + }, + }, + }; + } - setState(state) { - this.title = state.title || ''; - const type = state.type || this.type; - if (_.isString(type)) { - this.type = visTypes.get(type); - if (!this.type) { - throw new Error(`Invalid type "${type}"`); - } - } else { - this.type = type; + setState(state) { + this.title = state.title || ''; + const type = state.type || this.type; + if (_.isString(type)) { + this.type = visTypes.get(type); + if (!this.type) { + throw new Error(`Invalid type "${type}"`); } - - this.params = _.defaultsDeep({}, - _.cloneDeep(state.params || {}), - _.cloneDeep(this.type.visConfig.defaults || {}) - ); + } else { + this.type = type; } - setCurrentState(state) { - this.setState(state); - } + this.params = _.defaultsDeep({}, + _.cloneDeep(state.params || {}), + _.cloneDeep(this.type.visConfig.defaults || {}) + ); + } - getState() { - return { - title: this.title, - type: this.type.name, - params: _.cloneDeep(this.params), - }; - } + setCurrentState(state) { + this.setState(state); + } - updateState() { - this.emit('update'); - } + getState() { + return { + title: this.title, + type: this.type.name, + params: _.cloneDeep(this.params), + }; + } - forceReload() { - this.emit('reload'); - } + updateState() { + this.emit('update'); + } - isHierarchical() { - if (_.isFunction(this.type.hierarchicalData)) { - return !!this.type.hierarchicalData(this); - } else { - return !!this.type.hierarchicalData; - } - } + forceReload() { + this.emit('reload'); + } - hasUiState() { - return !!this.__uiState; + isHierarchical() { + if (_.isFunction(this.type.hierarchicalData)) { + return !!this.type.hierarchicalData(this); + } else { + return !!this.type.hierarchicalData; } + } - /*** - * this should not be used outside of visualize - * @param uiState - * @private - */ - _setUiState(uiState) { - if (uiState instanceof PersistedState) { - this.__uiState = uiState; - } - } + hasUiState() { + return !!this.__uiState; + } - getUiState() { - return this.__uiState; + /*** + * this should not be used outside of visualize + * @param uiState + * @private + */ + _setUiState(uiState) { + if (uiState instanceof PersistedState) { + this.__uiState = uiState; } + } - /** - * Currently this is only used to extract map-specific information - * (e.g. mapZoom, mapCenter). - */ - uiStateVal(key, val) { - if (this.hasUiState()) { - if (_.isUndefined(val)) { - return this.__uiState.get(key); - } - return this.__uiState.set(key, val); + getUiState() { + return this.__uiState; + } + + /** + * Currently this is only used to extract map-specific information + * (e.g. mapZoom, mapCenter). + */ + uiStateVal(key, val) { + if (this.hasUiState()) { + if (_.isUndefined(val)) { + return this.__uiState.get(key); } - return val; + return this.__uiState.set(key, val); } + return val; } - - return Vis; }