diff --git a/docs/development/plugins/embeddable/public/kibana-plugin-plugins-embeddable-public.embeddableinput.md b/docs/development/plugins/embeddable/public/kibana-plugin-plugins-embeddable-public.embeddableinput.md index d1d97d50f5948..f36f7b4ee77a4 100644 --- a/docs/development/plugins/embeddable/public/kibana-plugin-plugins-embeddable-public.embeddableinput.md +++ b/docs/development/plugins/embeddable/public/kibana-plugin-plugins-embeddable-public.embeddableinput.md @@ -19,5 +19,6 @@ export declare type EmbeddableInput = { timeRange?: TimeRange; query?: Query; filters?: Filter[]; + searchSessionId?: string; }; ``` diff --git a/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrenderer.md b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrenderer.md index 66c2e1e3c0c8d..32a7151578658 100644 --- a/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrenderer.md +++ b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrenderer.md @@ -7,5 +7,5 @@ Signature: ```typescript -ReactExpressionRenderer: ({ className, dataAttrs, padding, renderError, expression, onEvent, reload$, ...expressionLoaderOptions }: ReactExpressionRendererProps) => JSX.Element +ReactExpressionRenderer: ({ className, dataAttrs, padding, renderError, expression, onEvent, reload$, debounce, ...expressionLoaderOptions }: ReactExpressionRendererProps) => JSX.Element ``` diff --git a/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.debounce.md b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.debounce.md new file mode 100644 index 0000000000000..3f7eb12fbb7a8 --- /dev/null +++ b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.debounce.md @@ -0,0 +1,11 @@ + + +[Home](./index.md) > [kibana-plugin-plugins-expressions-public](./kibana-plugin-plugins-expressions-public.md) > [ReactExpressionRendererProps](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.md) > [debounce](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.debounce.md) + +## ReactExpressionRendererProps.debounce property + +Signature: + +```typescript +debounce?: number; +``` diff --git a/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.md b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.md index 5622516530edd..e4980ce04b9e2 100644 --- a/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.md +++ b/docs/development/plugins/expressions/public/kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.md @@ -16,6 +16,7 @@ export interface ReactExpressionRendererProps extends IExpressionLoaderParams | --- | --- | --- | | [className](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.classname.md) | string | | | [dataAttrs](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.dataattrs.md) | string[] | | +| [debounce](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.debounce.md) | number | | | [expression](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.expression.md) | string | ExpressionAstExpression | | | [onEvent](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.onevent.md) | (event: ExpressionRendererEvent) => void | | | [padding](./kibana-plugin-plugins-expressions-public.reactexpressionrendererprops.padding.md) | 'xs' | 's' | 'm' | 'l' | 'xl' | | diff --git a/docs/migration/migrate_8_0.asciidoc b/docs/migration/migrate_8_0.asciidoc index 0cb28ce0fb6e7..ef76121b21d29 100644 --- a/docs/migration/migrate_8_0.asciidoc +++ b/docs/migration/migrate_8_0.asciidoc @@ -167,4 +167,14 @@ The `xpack.` prefix has been removed for all telemetry configurations. *Impact:* For any configurations beginning with `xpack.telemetry`, remove the `xpack` prefix. Use {kibana-ref}/telemetry-settings-kbn.html#telemetry-general-settings[`telemetry.enabled`] instead. +[float] +=== SysV init support has been removed + +*Details:* +All supported operating systems support using systemd service files. Any system that doesn't already have service aliased to use kibana.service should use `systemctl start kibana.service` instead of the `service start kibana`. + +*Impact:* +Any installations using `.deb` or `.rpm` packages using SysV will need to migrate to systemd. + + // end::notable-breaking-changes[] diff --git a/docs/setup/install/deb-init.asciidoc b/docs/setup/install/deb-init.asciidoc deleted file mode 100644 index 6e21b8f97cf7e..0000000000000 --- a/docs/setup/install/deb-init.asciidoc +++ /dev/null @@ -1,20 +0,0 @@ -==== Run {kib} with SysV `init` - -Use the `update-rc.d` command to configure Kibana to start automatically -when the system boots up: - -[source,sh] --------------------------------------------------- -sudo update-rc.d kibana defaults 95 10 --------------------------------------------------- - -You can start and stop Kibana using the `service` command: - -[source,sh] --------------------------------------------- -sudo -i service kibana start -sudo -i service kibana stop --------------------------------------------- - -If Kibana fails to start for any reason, it will print the reason for -failure to `STDOUT`. Log files can be found in `/var/log/kibana/`. diff --git a/docs/setup/install/deb.asciidoc b/docs/setup/install/deb.asciidoc index 234c02cee0be1..c830faf1432d7 100644 --- a/docs/setup/install/deb.asciidoc +++ b/docs/setup/install/deb.asciidoc @@ -160,15 +160,7 @@ https://artifacts.elastic.co/downloads/kibana/kibana-oss-{version}-amd64.deb endif::[] -==== SysV `init` vs `systemd` - -include::init-systemd.asciidoc[] - -[[deb-running-init]] -include::deb-init.asciidoc[] - [[deb-running-systemd]] - include::systemd.asciidoc[] [[deb-configuring]] diff --git a/docs/setup/install/rpm-init.asciidoc b/docs/setup/install/rpm-init.asciidoc deleted file mode 100644 index 08282635a014f..0000000000000 --- a/docs/setup/install/rpm-init.asciidoc +++ /dev/null @@ -1,20 +0,0 @@ -==== Run {kib} with SysV `init` - -Use the `chkconfig` command to configure Kibana to start automatically -when the system boots up: - -[source,sh] --------------------------------------------------- -sudo chkconfig --add kibana --------------------------------------------------- - -You can start and stop Kibana using the `service` command: - -[source,sh] --------------------------------------------- -sudo -i service kibana start -sudo -i service kibana stop --------------------------------------------- - -If Kibana fails to start for any reason, it will print the reason for -failure to `STDOUT`. Log files can be found in `/var/log/kibana/`. diff --git a/docs/setup/install/rpm.asciidoc b/docs/setup/install/rpm.asciidoc index 1153353aa9a0f..0b63684808d7d 100644 --- a/docs/setup/install/rpm.asciidoc +++ b/docs/setup/install/rpm.asciidoc @@ -153,13 +153,6 @@ https://artifacts.elastic.co/downloads/kibana/kibana-oss-{version}-x86_64.rpm endif::[] -==== SysV `init` vs `systemd` - -include::init-systemd.asciidoc[] - -[[rpm-running-init]] -include::rpm-init.asciidoc[] - [[rpm-running-systemd]] include::systemd.asciidoc[] diff --git a/docs/setup/start-stop.asciidoc b/docs/setup/start-stop.asciidoc index 198bc76bbb400..8952cd3a23cd3 100644 --- a/docs/setup/start-stop.asciidoc +++ b/docs/setup/start-stop.asciidoc @@ -25,25 +25,8 @@ stop and start {kib} from the command line. include::install/windows-running.asciidoc[] [float] -[[start-stop-deb]] -=== Debian packages - -include::install/init-systemd.asciidoc[] - -[float] -include::install/deb-init.asciidoc[] - -[float] -include::install/systemd.asciidoc[] - -[float] -[[start-stop-rpm]] -=== RPM packages - -include::install/init-systemd.asciidoc[] - -[float] -include::install/rpm-init.asciidoc[] +[[start-stop-deb-rpm]] +=== Debian and RPM packages [float] include::install/systemd.asciidoc[] diff --git a/packages/kbn-optimizer/limits.yml b/packages/kbn-optimizer/limits.yml index c660d37222504..3f9fdb164e759 100644 --- a/packages/kbn-optimizer/limits.yml +++ b/packages/kbn-optimizer/limits.yml @@ -14,7 +14,7 @@ pageLoadAssetSize: dashboard: 374194 dashboardEnhanced: 65646 dashboardMode: 22716 - data: 1287839 + data: 1317839 dataEnhanced: 50420 devTools: 38637 discover: 105145 diff --git a/src/dev/build/tasks/os_packages/run_fpm.ts b/src/dev/build/tasks/os_packages/run_fpm.ts index b8289f1da194f..e5de760ea11d0 100644 --- a/src/dev/build/tasks/os_packages/run_fpm.ts +++ b/src/dev/build/tasks/os_packages/run_fpm.ts @@ -134,7 +134,6 @@ export async function runFpm( `${resolveWithTrailingSlash(fromBuild('data'))}=/var/lib/kibana/`, // copy package configurations - `${resolveWithTrailingSlash(__dirname, 'service_templates/sysv/')}=/`, `${resolveWithTrailingSlash(__dirname, 'service_templates/systemd/')}=/`, ]; diff --git a/src/dev/build/tasks/os_packages/service_templates/sysv/etc/default/kibana b/src/dev/build/tasks/os_packages/service_templates/systemd/etc/default/kibana similarity index 100% rename from src/dev/build/tasks/os_packages/service_templates/sysv/etc/default/kibana rename to src/dev/build/tasks/os_packages/service_templates/systemd/etc/default/kibana diff --git a/src/dev/build/tasks/os_packages/service_templates/sysv/etc/init.d/kibana b/src/dev/build/tasks/os_packages/service_templates/sysv/etc/init.d/kibana deleted file mode 100755 index eedd4898ce6c3..0000000000000 --- a/src/dev/build/tasks/os_packages/service_templates/sysv/etc/init.d/kibana +++ /dev/null @@ -1,174 +0,0 @@ -#!/bin/sh -# Init script for kibana -# Maintained by -# Generated by pleaserun. -# Implemented based on LSB Core 3.1: -# * Sections: 20.2, 20.3 -# -### BEGIN INIT INFO -# Provides: kibana -# Required-Start: $remote_fs $syslog -# Required-Stop: $remote_fs $syslog -# Default-Start: 2 3 4 5 -# Default-Stop: 0 1 6 -# Short-Description: -# Description: Kibana -### END INIT INFO - -# -# Source function libraries if present. -# (It improves integration with systemd) -# -# Red Hat -if [ -f /etc/rc.d/init.d/functions ]; then - . /etc/rc.d/init.d/functions - -# Debian -elif [ -f /lib/lsb/init-functions ]; then - . /lib/lsb/init-functions - -# SUSE -elif [ -f /etc/rc.status ]; then - . /etc/rc.status - rc_reset -fi - -name=kibana -program=/usr/share/kibana/bin/kibana -args="--logging.dest=/var/log/kibana/kibana.log" -pidfile="/var/run/kibana/$name.pid" - -[ -r /etc/default/$name ] && . /etc/default/$name -[ -r /etc/sysconfig/$name ] && . /etc/sysconfig/$name - -export KBN_PATH_CONF -export NODE_OPTIONS - -[ -z "$nice" ] && nice=0 - -trace() { - logger -t "/etc/init.d/kibana" "$@" -} - -emit() { - trace "$@" - echo "$@" -} - -start() { - [ ! -d "/var/run/kibana/" ] && mkdir "/var/run/kibana/" - chown "$user":"$group" "/var/run/kibana/" - chmod 755 "/var/run/kibana/" - - chroot --userspec "$user":"$group" "$chroot" sh -c " - - cd \"$chdir\" - exec \"$program $args\" - " >> /var/log/kibana/kibana.log 2>&1 & - - # Generate the pidfile from here. If we instead made the forked process - # generate it there will be a race condition between the pidfile writing - # and a process possibly asking for status. - echo $! > $pidfile - - emit "$name started" - return 0 -} - -stop() { - # Try a few times to kill TERM the program - if status ; then - pid=$(cat "$pidfile") - trace "Killing $name (pid $pid) with SIGTERM" - kill -TERM $pid - # Wait for it to exit. - for i in 1 2 3 4 5 ; do - trace "Waiting $name (pid $pid) to die..." - status || break - sleep 1 - done - if status ; then - if [ "$KILL_ON_STOP_TIMEOUT" -eq 1 ] ; then - trace "Timeout reached. Killing $name (pid $pid) with SIGKILL. This may result in data loss." - kill -KILL $pid - emit "$name killed with SIGKILL." - else - emit "$name stop failed; still running." - fi - else - emit "$name stopped." - fi - fi -} - -status() { - if [ -f "$pidfile" ] ; then - pid=$(cat "$pidfile") - if ps -p $pid > /dev/null 2> /dev/null ; then - # process by this pid is running. - # It may not be our pid, but that's what you get with just pidfiles. - # TODO(sissel): Check if this process seems to be the same as the one we - # expect. It'd be nice to use flock here, but flock uses fork, not exec, - # so it makes it quite awkward to use in this case. - return 0 - else - return 2 # program is dead but pid file exists - fi - else - return 3 # program is not running - fi -} - -force_stop() { - if status ; then - stop - status && kill -KILL $(cat "$pidfile") - fi -} - - -case "$1" in - force-start|start|stop|force-stop|restart) - trace "Attempting '$1' on kibana" - ;; -esac - -case "$1" in - force-start) - PRESTART=no - exec "$0" start - ;; - start) - status - code=$? - if [ $code -eq 0 ]; then - emit "$name is already running" - exit $code - else - start - exit $? - fi - ;; - stop) stop ;; - force-stop) force_stop ;; - status) - status - code=$? - if [ $code -eq 0 ] ; then - emit "$name is running" - else - emit "$name is not running" - fi - exit $code - ;; - restart) - - stop && start - ;; - *) - echo "Usage: $SCRIPTNAME {start|force-start|stop|force-start|force-stop|status|restart}" >&2 - exit 3 - ;; -esac - -exit $? diff --git a/src/plugins/dashboard/public/application/dashboard_app_controller.tsx b/src/plugins/dashboard/public/application/dashboard_app_controller.tsx index fa45e433050ab..e5947b73b305b 100644 --- a/src/plugins/dashboard/public/application/dashboard_app_controller.tsx +++ b/src/plugins/dashboard/public/application/dashboard_app_controller.tsx @@ -139,7 +139,7 @@ export class DashboardAppController { dashboardCapabilities, scopedHistory, embeddableCapabilities: { visualizeCapabilities, mapsCapabilities }, - data: { query: queryService }, + data: { query: queryService, search: searchService }, core: { notifications, overlays, @@ -412,8 +412,9 @@ export class DashboardAppController { >(DASHBOARD_CONTAINER_TYPE); if (dashboardFactory) { + const searchSessionId = searchService.session.start(); dashboardFactory - .create(getDashboardInput()) + .create({ ...getDashboardInput(), searchSessionId }) .then((container: DashboardContainer | ErrorEmbeddable | undefined) => { if (container && !isErrorEmbeddable(container)) { dashboardContainer = container; @@ -572,7 +573,7 @@ export class DashboardAppController { differences.filters = appStateDashboardInput.filters; } - Object.keys(_.omit(containerInput, ['filters'])).forEach((key) => { + Object.keys(_.omit(containerInput, ['filters', 'searchSessionId'])).forEach((key) => { const containerValue = (containerInput as { [key: string]: unknown })[key]; const appStateValue = ((appStateDashboardInput as unknown) as { [key: string]: unknown })[ key @@ -590,7 +591,8 @@ export class DashboardAppController { const refreshDashboardContainer = () => { const changes = getChangesFromAppStateForContainerState(); if (changes && dashboardContainer) { - dashboardContainer.updateInput(changes); + const searchSessionId = searchService.session.start(); + dashboardContainer.updateInput({ ...changes, searchSessionId }); } }; @@ -1109,12 +1111,6 @@ export class DashboardAppController { $scope.model.filters = filterManager.getFilters(); $scope.model.query = queryStringManager.getQuery(); dashboardStateManager.applyFilters($scope.model.query, $scope.model.filters); - if (dashboardContainer) { - dashboardContainer.updateInput({ - filters: $scope.model.filters, - query: $scope.model.query, - }); - } }, }); @@ -1159,6 +1155,7 @@ export class DashboardAppController { if (dashboardContainer) { dashboardContainer.destroy(); } + searchService.session.clear(); }); } } diff --git a/src/plugins/dashboard/public/application/embeddable/dashboard_container.test.tsx b/src/plugins/dashboard/public/application/embeddable/dashboard_container.test.tsx index a7226082d3dce..89aacf2a84029 100644 --- a/src/plugins/dashboard/public/application/embeddable/dashboard_container.test.tsx +++ b/src/plugins/dashboard/public/application/embeddable/dashboard_container.test.tsx @@ -134,3 +134,25 @@ test('Container view mode change propagates to new children', async () => { expect(embeddable.getInput().viewMode).toBe(ViewMode.EDIT); }); + +test('searchSessionId propagates to children', async () => { + const searchSessionId1 = 'searchSessionId1'; + const container = new DashboardContainer( + getSampleDashboardInput({ searchSessionId: searchSessionId1 }), + options + ); + const embeddable = await container.addNewEmbeddable< + ContactCardEmbeddableInput, + ContactCardEmbeddableOutput, + ContactCardEmbeddable + >(CONTACT_CARD_EMBEDDABLE, { + firstName: 'Bob', + }); + + expect(embeddable.getInput().searchSessionId).toBe(searchSessionId1); + + const searchSessionId2 = 'searchSessionId2'; + container.updateInput({ searchSessionId: searchSessionId2 }); + + expect(embeddable.getInput().searchSessionId).toBe(searchSessionId2); +}); diff --git a/src/plugins/dashboard/public/application/embeddable/dashboard_container.tsx b/src/plugins/dashboard/public/application/embeddable/dashboard_container.tsx index 036880a1d088b..757488185fe8e 100644 --- a/src/plugins/dashboard/public/application/embeddable/dashboard_container.tsx +++ b/src/plugins/dashboard/public/application/embeddable/dashboard_container.tsx @@ -78,6 +78,7 @@ export interface InheritedChildInput extends IndexSignature { viewMode: ViewMode; hidePanelTitles?: boolean; id: string; + searchSessionId?: string; } export interface DashboardContainerOptions { @@ -228,7 +229,15 @@ export class DashboardContainer extends Container { }; startDeps = { getConfig: jest.fn(), + getIndexPattern: jest.fn(), + isDefaultTimezone: jest.fn(), }; }); @@ -201,8 +203,9 @@ describe('Aggs service', () => { describe('start()', () => { test('exposes proper contract', () => { const start = service.start(startDeps); - expect(Object.keys(start).length).toBe(3); + expect(Object.keys(start).length).toBe(4); expect(start).toHaveProperty('calculateAutoTimeExpression'); + expect(start).toHaveProperty('getDateMetaByDatatableColumn'); expect(start).toHaveProperty('createAggConfigs'); expect(start).toHaveProperty('types'); }); diff --git a/src/plugins/data/common/search/aggs/aggs_service.ts b/src/plugins/data/common/search/aggs/aggs_service.ts index 6f3e3904dbbd5..b6afa708f9e6f 100644 --- a/src/plugins/data/common/search/aggs/aggs_service.ts +++ b/src/plugins/data/common/search/aggs/aggs_service.ts @@ -18,7 +18,7 @@ */ import { ExpressionsServiceSetup } from 'src/plugins/expressions/common'; -import { UI_SETTINGS } from '../../../common'; +import { IndexPattern, UI_SETTINGS } from '../../../common'; import { GetConfigFn } from '../../types'; import { AggConfigs, @@ -28,6 +28,7 @@ import { getCalculateAutoTimeExpression, } from './'; import { AggsCommonSetup, AggsCommonStart } from './types'; +import { getDateMetaByDatatableColumn } from './utils/time_column_meta'; /** @internal */ export const aggsRequiredUiSettings = [ @@ -50,6 +51,8 @@ export interface AggsCommonSetupDependencies { /** @internal */ export interface AggsCommonStartDependencies { getConfig: GetConfigFn; + getIndexPattern(id: string): Promise; + isDefaultTimezone: () => boolean; } /** @@ -77,11 +80,22 @@ export class AggsCommonService { }; } - public start({ getConfig }: AggsCommonStartDependencies): AggsCommonStart { + public start({ + getConfig, + getIndexPattern, + isDefaultTimezone, + }: AggsCommonStartDependencies): AggsCommonStart { const aggTypesStart = this.aggTypesRegistry.start(); + const calculateAutoTimeExpression = getCalculateAutoTimeExpression(getConfig); return { - calculateAutoTimeExpression: getCalculateAutoTimeExpression(getConfig), + calculateAutoTimeExpression, + getDateMetaByDatatableColumn: getDateMetaByDatatableColumn({ + calculateAutoTimeExpression, + getIndexPattern, + getConfig, + isDefaultTimezone, + }), createAggConfigs: (indexPattern, configStates = [], schemas) => { return new AggConfigs(indexPattern, configStates, { typesRegistry: aggTypesStart, diff --git a/src/plugins/data/common/search/aggs/buckets/date_histogram.ts b/src/plugins/data/common/search/aggs/buckets/date_histogram.ts index c273ca53a5fed..694b03f660452 100644 --- a/src/plugins/data/common/search/aggs/buckets/date_histogram.ts +++ b/src/plugins/data/common/search/aggs/buckets/date_histogram.ts @@ -34,6 +34,7 @@ import { writeParams } from '../agg_params'; import { isMetricAggType } from '../metrics/metric_agg_type'; import { BaseAggParams } from '../types'; import { dateHistogramInterval } from '../utils'; +import { inferTimeZone } from '../utils'; /** @internal */ export type CalculateBoundsFn = (timeRange: TimeRange) => TimeRangeBounds; @@ -235,25 +236,7 @@ export const getDateHistogramBucketAgg = ({ // time_zones being persisted into saved_objects serialize: noop, write(agg, output) { - // If a time_zone has been set explicitly always prefer this. - let tz = agg.params.time_zone; - if (!tz && agg.params.field) { - // If a field has been configured check the index pattern's typeMeta if a date_histogram on that - // field requires a specific time_zone - tz = get(agg.getIndexPattern(), [ - 'typeMeta', - 'aggs', - 'date_histogram', - agg.params.field.name, - 'time_zone', - ]); - } - if (!tz) { - // If the index pattern typeMeta data, didn't had a time zone assigned for the selected field use the configured tz - const detectedTimezone = moment.tz.guess(); - const tzOffset = moment().format('Z'); - tz = isDefaultTimezone() ? detectedTimezone || tzOffset : getConfig('dateFormat:tz'); - } + const tz = inferTimeZone(agg.params, agg.getIndexPattern(), isDefaultTimezone, getConfig); output.params.time_zone = tz; }, }, diff --git a/src/plugins/data/common/search/aggs/types.ts b/src/plugins/data/common/search/aggs/types.ts index aec3dcc9d068c..09a13762d4d70 100644 --- a/src/plugins/data/common/search/aggs/types.ts +++ b/src/plugins/data/common/search/aggs/types.ts @@ -18,7 +18,9 @@ */ import { Assign } from '@kbn/utility-types'; +import { DatatableColumn } from 'src/plugins/expressions'; import { IndexPattern } from '../../index_patterns/index_patterns/index_pattern'; +import { TimeRange } from '../../query'; import { AggConfigSerialized, AggConfigs, @@ -80,6 +82,19 @@ export interface AggsCommonSetup { /** @internal */ export interface AggsCommonStart { calculateAutoTimeExpression: ReturnType; + /** + * Helper function returning meta data about use date intervals for a data table column. + * If the column is not a column created by a date histogram aggregation of the esaggs data source, + * this function will return undefined. + * + * Otherwise, it will return the following attributes in an object: + * * `timeZone` time zone used to create the buckets (important e.g. for DST), + * * `timeRange` total time range of the fetch data (to infer partial buckets at the beginning and end of the data) + * * `interval` Interval used on elasticsearch (`auto` resolved to the actual interval) + */ + getDateMetaByDatatableColumn: ( + column: DatatableColumn + ) => Promise; createAggConfigs: ( indexPattern: IndexPattern, configStates?: CreateAggConfigParams[], diff --git a/src/plugins/data/common/search/aggs/utils/index.ts b/src/plugins/data/common/search/aggs/utils/index.ts index 99ce44207d80d..7d6cb1c7ef33f 100644 --- a/src/plugins/data/common/search/aggs/utils/index.ts +++ b/src/plugins/data/common/search/aggs/utils/index.ts @@ -23,3 +23,4 @@ export * from './get_format_with_aggs'; export * from './ipv4_address'; export * from './prop_filter'; export * from './to_angular_json'; +export * from './infer_time_zone'; diff --git a/src/plugins/data/common/search/aggs/utils/infer_time_zone.test.ts b/src/plugins/data/common/search/aggs/utils/infer_time_zone.test.ts new file mode 100644 index 0000000000000..8fc3726ee1b32 --- /dev/null +++ b/src/plugins/data/common/search/aggs/utils/infer_time_zone.test.ts @@ -0,0 +1,79 @@ +/* + * 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. + */ + +jest.mock('moment', () => { + const moment: any = jest.fn(() => { + return { + format: jest.fn(() => '-1;00'), + }; + }); + moment.tz = { + guess: jest.fn(() => 'CET'), + }; + return moment; +}); + +import { IndexPattern } from '../../../index_patterns'; +import { AggParamsDateHistogram } from '../buckets'; +import { inferTimeZone } from './infer_time_zone'; + +describe('inferTimeZone', () => { + it('reads time zone from agg params', () => { + const params: AggParamsDateHistogram = { + time_zone: 'CEST', + }; + expect(inferTimeZone(params, {} as IndexPattern, () => false, jest.fn())).toEqual('CEST'); + }); + + it('reads time zone from index pattern type meta if available', () => { + expect( + inferTimeZone( + { field: 'mydatefield' }, + ({ + typeMeta: { + aggs: { + date_histogram: { + mydatefield: { + time_zone: 'UTC', + }, + }, + }, + }, + } as unknown) as IndexPattern, + () => false, + jest.fn() + ) + ).toEqual('UTC'); + }); + + it('reads time zone from moment if set to default', () => { + expect(inferTimeZone({}, {} as IndexPattern, () => true, jest.fn())).toEqual('CET'); + }); + + it('reads time zone from config if not set to default', () => { + expect( + inferTimeZone( + {}, + {} as IndexPattern, + () => false, + () => 'CET' as any + ) + ).toEqual('CET'); + }); +}); diff --git a/src/plugins/data/common/search/aggs/utils/infer_time_zone.ts b/src/plugins/data/common/search/aggs/utils/infer_time_zone.ts new file mode 100644 index 0000000000000..282238c5a0459 --- /dev/null +++ b/src/plugins/data/common/search/aggs/utils/infer_time_zone.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 moment from 'moment'; +import { IndexPattern } from '../../../index_patterns'; +import { AggParamsDateHistogram } from '../buckets'; + +export function inferTimeZone( + params: AggParamsDateHistogram, + indexPattern: IndexPattern, + isDefaultTimezone: () => boolean, + getConfig: (key: string) => T +) { + let tz = params.time_zone; + if (!tz && params.field) { + // If a field has been configured check the index pattern's typeMeta if a date_histogram on that + // field requires a specific time_zone + tz = indexPattern.typeMeta?.aggs?.date_histogram?.[params.field]?.time_zone; + } + if (!tz) { + // If the index pattern typeMeta data, didn't had a time zone assigned for the selected field use the configured tz + const detectedTimezone = moment.tz.guess(); + const tzOffset = moment().format('Z'); + tz = isDefaultTimezone() + ? detectedTimezone || tzOffset + : // if timezone is not the default, this will always return a string + (getConfig('dateFormat:tz') as string); + } + return tz; +} diff --git a/src/plugins/data/common/search/aggs/utils/time_column_meta.test.ts b/src/plugins/data/common/search/aggs/utils/time_column_meta.test.ts new file mode 100644 index 0000000000000..e56d622734554 --- /dev/null +++ b/src/plugins/data/common/search/aggs/utils/time_column_meta.test.ts @@ -0,0 +1,121 @@ +/* + * 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 { BUCKET_TYPES } from '../buckets'; +import { DateMetaByColumnDeps, getDateMetaByDatatableColumn } from './time_column_meta'; + +describe('getDateMetaByDatatableColumn', () => { + let params: DateMetaByColumnDeps; + beforeEach(() => { + params = { + calculateAutoTimeExpression: jest.fn().mockReturnValue('5m'), + getIndexPattern: jest.fn().mockResolvedValue({}), + isDefaultTimezone: jest.fn().mockReturnValue(true), + getConfig: jest.fn(), + }; + }); + + it('returns nothing on column from other data source', async () => { + expect( + await getDateMetaByDatatableColumn(params)({ + id: 'test', + name: 'test', + meta: { + type: 'date', + source: 'essql', + }, + }) + ).toEqual(undefined); + }); + + it('returns nothing on non date histogram column', async () => { + expect( + await getDateMetaByDatatableColumn(params)({ + id: 'test', + name: 'test', + meta: { + type: 'date', + source: 'esaggs', + sourceParams: { + type: BUCKET_TYPES.TERMS, + }, + }, + }) + ).toEqual(undefined); + }); + + it('returns time range, time zone and interval', async () => { + expect( + await getDateMetaByDatatableColumn(params)({ + id: 'test', + name: 'test', + meta: { + type: 'date', + source: 'esaggs', + sourceParams: { + type: BUCKET_TYPES.DATE_HISTOGRAM, + params: { + time_zone: 'UTC', + interval: '1h', + }, + appliedTimeRange: { + from: 'now-5d', + to: 'now', + }, + }, + }, + }) + ).toEqual({ + timeZone: 'UTC', + timeRange: { + from: 'now-5d', + to: 'now', + }, + interval: '1h', + }); + }); + + it('returns resolved auto interval', async () => { + expect( + await getDateMetaByDatatableColumn(params)({ + id: 'test', + name: 'test', + meta: { + type: 'date', + source: 'esaggs', + sourceParams: { + type: BUCKET_TYPES.DATE_HISTOGRAM, + params: { + time_zone: 'UTC', + interval: 'auto', + }, + appliedTimeRange: { + from: 'now-5d', + to: 'now', + }, + }, + }, + }) + ).toEqual( + expect.objectContaining({ + interval: '5m', + }) + ); + }); +}); diff --git a/src/plugins/data/common/search/aggs/utils/time_column_meta.ts b/src/plugins/data/common/search/aggs/utils/time_column_meta.ts new file mode 100644 index 0000000000000..1bea716c6a049 --- /dev/null +++ b/src/plugins/data/common/search/aggs/utils/time_column_meta.ts @@ -0,0 +1,66 @@ +/* + * 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 { DatatableColumn } from 'src/plugins/expressions/common'; +import { IndexPattern } from '../../../index_patterns'; + +import { TimeRange } from '../../../types'; +import { AggParamsDateHistogram, BUCKET_TYPES } from '../buckets'; +import { inferTimeZone } from './infer_time_zone'; + +export interface DateMetaByColumnDeps { + calculateAutoTimeExpression: (range: TimeRange) => string | undefined; + getIndexPattern: (id: string) => Promise; + isDefaultTimezone: () => boolean; + getConfig: (key: string) => T; +} + +export const getDateMetaByDatatableColumn = ({ + calculateAutoTimeExpression, + getIndexPattern, + isDefaultTimezone, + getConfig, +}: DateMetaByColumnDeps) => async ( + column: DatatableColumn +): Promise => { + if (column.meta.source !== 'esaggs') return; + if (column.meta.sourceParams?.type !== BUCKET_TYPES.DATE_HISTOGRAM) return; + const params = column.meta.sourceParams.params as AggParamsDateHistogram; + const appliedTimeRange = column.meta.sourceParams.appliedTimeRange as TimeRange; + + const tz = inferTimeZone( + params, + await getIndexPattern(column.meta.sourceParams.indexPatternId as string), + isDefaultTimezone, + getConfig + ); + + const interval = + params.interval === 'auto' ? calculateAutoTimeExpression(appliedTimeRange) : params.interval; + + if (!interval) { + throw new Error('time interval could not be determined'); + } + + return { + timeZone: tz, + timeRange: appliedTimeRange, + interval, + }; +}; diff --git a/src/plugins/data/public/public.api.md b/src/plugins/data/public/public.api.md index 81fa6d4ba20db..7ee21236c1c79 100644 --- a/src/plugins/data/public/public.api.md +++ b/src/plugins/data/public/public.api.md @@ -16,6 +16,7 @@ import { CoreSetup } from 'src/core/public'; import { CoreSetup as CoreSetup_2 } from 'kibana/public'; import { CoreStart } from 'kibana/public'; import { CoreStart as CoreStart_2 } from 'src/core/public'; +import { DatatableColumn as DatatableColumn_2 } from 'src/plugins/expressions'; import { Ensure } from '@kbn/utility-types'; import { EnvironmentMode } from '@kbn/config'; import { ErrorToastOptions } from 'src/core/public/notifications'; @@ -2285,7 +2286,7 @@ export const UI_SETTINGS: { // src/plugins/data/common/es_query/filters/phrase_filter.ts:33:3 - (ae-forgotten-export) The symbol "PhraseFilterMeta" needs to be exported by the entry point index.d.ts // src/plugins/data/common/es_query/filters/phrases_filter.ts:31:3 - (ae-forgotten-export) The symbol "PhrasesFilterMeta" needs to be exported by the entry point index.d.ts // src/plugins/data/common/index_patterns/index_patterns/index_pattern.ts:62:5 - (ae-forgotten-export) The symbol "FormatFieldFn" needs to be exported by the entry point index.d.ts -// src/plugins/data/common/search/aggs/types.ts:98:51 - (ae-forgotten-export) The symbol "AggTypesRegistryStart" needs to be exported by the entry point index.d.ts +// src/plugins/data/common/search/aggs/types.ts:113:51 - (ae-forgotten-export) The symbol "AggTypesRegistryStart" needs to be exported by the entry point index.d.ts // src/plugins/data/public/field_formats/field_formats_service.ts:67:3 - (ae-forgotten-export) The symbol "FormatFactory" needs to be exported by the entry point index.d.ts // src/plugins/data/public/index.ts:66:23 - (ae-forgotten-export) The symbol "FILTERS" needs to be exported by the entry point index.d.ts // src/plugins/data/public/index.ts:66:23 - (ae-forgotten-export) The symbol "getDisplayValueFromFilter" needs to be exported by the entry point index.d.ts diff --git a/src/plugins/data/public/search/aggs/aggs_service.test.ts b/src/plugins/data/public/search/aggs/aggs_service.test.ts index db25dfb300d11..de747d234b441 100644 --- a/src/plugins/data/public/search/aggs/aggs_service.test.ts +++ b/src/plugins/data/public/search/aggs/aggs_service.test.ts @@ -23,6 +23,7 @@ import { coreMock } from '../../../../../core/public/mocks'; import { expressionsPluginMock } from '../../../../../plugins/expressions/public/mocks'; import { BucketAggType, getAggTypes, MetricAggType } from '../../../common'; import { fieldFormatsServiceMock } from '../../field_formats/mocks'; +import { dataPluginMock } from '../../mocks'; import { AggsService, @@ -46,6 +47,7 @@ describe('AggsService - public', () => { }; startDeps = { fieldFormats: fieldFormatsServiceMock.createStartContract(), + indexPatterns: dataPluginMock.createStartContract().indexPatterns, uiSettings, }; }); @@ -86,8 +88,9 @@ describe('AggsService - public', () => { describe('start()', () => { test('exposes proper contract', () => { const start = service.start(startDeps); - expect(Object.keys(start).length).toBe(3); + expect(Object.keys(start).length).toBe(4); expect(start).toHaveProperty('calculateAutoTimeExpression'); + expect(start).toHaveProperty('getDateMetaByDatatableColumn'); expect(start).toHaveProperty('createAggConfigs'); expect(start).toHaveProperty('types'); }); diff --git a/src/plugins/data/public/search/aggs/aggs_service.ts b/src/plugins/data/public/search/aggs/aggs_service.ts index 4b088ddfe314f..85e0f604bb8b5 100644 --- a/src/plugins/data/public/search/aggs/aggs_service.ts +++ b/src/plugins/data/public/search/aggs/aggs_service.ts @@ -32,6 +32,7 @@ import { AggTypesDependencies, } from '../../../common/search/aggs'; import { AggsSetup, AggsStart } from './types'; +import { IndexPatternsContract } from '../../index_patterns'; /** * Aggs needs synchronous access to specific uiSettings. Since settings can change @@ -68,6 +69,7 @@ export interface AggsSetupDependencies { export interface AggsStartDependencies { fieldFormats: FieldFormatsStart; uiSettings: IUiSettingsClient; + indexPatterns: IndexPatternsContract; } /** @@ -94,9 +96,17 @@ export class AggsService { return this.aggsCommonService.setup({ registerFunction }); } - public start({ fieldFormats, uiSettings }: AggsStartDependencies): AggsStart { - const { calculateAutoTimeExpression, types } = this.aggsCommonService.start({ + public start({ fieldFormats, uiSettings, indexPatterns }: AggsStartDependencies): AggsStart { + const isDefaultTimezone = () => uiSettings.isDefault('dateFormat:tz'); + + const { + calculateAutoTimeExpression, + getDateMetaByDatatableColumn, + types, + } = this.aggsCommonService.start({ getConfig: this.getConfig!, + getIndexPattern: indexPatterns.get, + isDefaultTimezone, }); const aggTypesDependencies: AggTypesDependencies = { @@ -106,7 +116,7 @@ export class AggsService { deserialize: fieldFormats.deserialize, getDefaultInstance: fieldFormats.getDefaultInstance, }), - isDefaultTimezone: () => uiSettings.isDefault('dateFormat:tz'), + isDefaultTimezone, }; // initialize each agg type and store in memory @@ -137,6 +147,7 @@ export class AggsService { return { calculateAutoTimeExpression, + getDateMetaByDatatableColumn, createAggConfigs: (indexPattern, configStates = [], schemas) => { return new AggConfigs(indexPattern, configStates, { typesRegistry }); }, diff --git a/src/plugins/data/public/search/aggs/mocks.ts b/src/plugins/data/public/search/aggs/mocks.ts index ca13343777e63..abc930f00b594 100644 --- a/src/plugins/data/public/search/aggs/mocks.ts +++ b/src/plugins/data/public/search/aggs/mocks.ts @@ -67,6 +67,7 @@ export const searchAggsSetupMock = (): AggsSetup => ({ export const searchAggsStartMock = (): AggsStart => ({ calculateAutoTimeExpression: getCalculateAutoTimeExpression(getConfig), + getDateMetaByDatatableColumn: jest.fn(), createAggConfigs: jest.fn().mockImplementation((indexPattern, configStates = [], schemas) => { return new AggConfigs(indexPattern, configStates, { typesRegistry: mockAggTypesRegistry(), diff --git a/src/plugins/data/public/search/expressions/esaggs.ts b/src/plugins/data/public/search/expressions/esaggs.ts index de7a4ffce8bd4..dba77d398c8b6 100644 --- a/src/plugins/data/public/search/expressions/esaggs.ts +++ b/src/plugins/data/public/search/expressions/esaggs.ts @@ -65,6 +65,7 @@ export interface RequestHandlerParams { metricsAtAllLevels?: boolean; visParams?: any; abortSignal?: AbortSignal; + searchSessionId?: string; } const name = 'esaggs'; @@ -82,6 +83,7 @@ const handleCourierRequest = async ({ inspectorAdapters, filterManager, abortSignal, + searchSessionId, }: RequestHandlerParams) => { // Create a new search source that inherits the original search source // but has the appropriate timeRange applied via a filter. @@ -143,6 +145,7 @@ const handleCourierRequest = async ({ defaultMessage: 'This request queries Elasticsearch to fetch the data for the visualization.', }), + searchSessionId, } ); request.stats(getRequestInspectorStats(requestSearchSource)); @@ -150,6 +153,7 @@ const handleCourierRequest = async ({ try { const response = await requestSearchSource.fetch({ abortSignal, + sessionId: searchSessionId, }); request.stats(getResponseInspectorStats(response, searchSource)).ok({ json: response }); @@ -248,7 +252,7 @@ export const esaggs = (): EsaggsExpressionFunctionDefinition => ({ multi: true, }, }, - async fn(input, args, { inspectorAdapters, abortSignal }) { + async fn(input, args, { inspectorAdapters, abortSignal, getSearchSessionId }) { const indexPatterns = getIndexPatterns(); const { filterManager } = getQueryService(); const searchService = getSearchService(); @@ -276,6 +280,7 @@ export const esaggs = (): EsaggsExpressionFunctionDefinition => ({ inspectorAdapters: inspectorAdapters as Adapters, filterManager, abortSignal: (abortSignal as unknown) as AbortSignal, + searchSessionId: getSearchSessionId(), }); const table: Datatable = { @@ -293,6 +298,13 @@ export const esaggs = (): EsaggsExpressionFunctionDefinition => ({ source: 'esaggs', sourceParams: { indexPatternId: indexPattern.id, + appliedTimeRange: + column.aggConfig.params.field?.name && + input?.timeRange && + args.timeFields && + args.timeFields.includes(column.aggConfig.params.field?.name) + ? { from: input.timeRange.from, to: input.timeRange.to } + : undefined, ...column.aggConfig.serialize(), }, }, diff --git a/src/plugins/data/public/search/search_service.ts b/src/plugins/data/public/search/search_service.ts index f955dc5b6ebd5..3dbabfc68fdbc 100644 --- a/src/plugins/data/public/search/search_service.ts +++ b/src/plugins/data/public/search/search_service.ts @@ -143,7 +143,7 @@ export class SearchService implements Plugin { }; return { - aggs: this.aggsService.start({ fieldFormats, uiSettings }), + aggs: this.aggsService.start({ fieldFormats, uiSettings, indexPatterns }), search, showError: (e: Error) => { this.searchInterceptor.showError(e); diff --git a/src/plugins/data/server/index_patterns/mocks.ts b/src/plugins/data/server/index_patterns/mocks.ts index 8f95afe3b3c9d..52d8aa1e35093 100644 --- a/src/plugins/data/server/index_patterns/mocks.ts +++ b/src/plugins/data/server/index_patterns/mocks.ts @@ -19,6 +19,6 @@ export function createIndexPatternsStartMock() { return { - indexPatternsServiceFactory: jest.fn(), + indexPatternsServiceFactory: jest.fn().mockResolvedValue({ get: jest.fn() }), }; } diff --git a/src/plugins/data/server/search/aggs/aggs_service.test.ts b/src/plugins/data/server/search/aggs/aggs_service.test.ts index d9a945a15fb67..cb4239cc339c4 100644 --- a/src/plugins/data/server/search/aggs/aggs_service.test.ts +++ b/src/plugins/data/server/search/aggs/aggs_service.test.ts @@ -23,6 +23,7 @@ import { coreMock } from '../../../../../core/server/mocks'; import { expressionsPluginMock } from '../../../../../plugins/expressions/server/mocks'; import { BucketAggType, getAggTypes, MetricAggType } from '../../../common'; import { createFieldFormatsStartMock } from '../../field_formats/mocks'; +import { createIndexPatternsStartMock } from '../../index_patterns/mocks'; import { AggsService, AggsSetupDependencies, AggsStartDependencies } from './aggs_service'; @@ -40,6 +41,7 @@ describe('AggsService - server', () => { }; startDeps = { fieldFormats: createFieldFormatsStartMock(), + indexPatterns: createIndexPatternsStartMock(), uiSettings, }; }); diff --git a/src/plugins/data/server/search/aggs/aggs_service.ts b/src/plugins/data/server/search/aggs/aggs_service.ts index 3e5cd8adb44a6..c805c8af6694c 100644 --- a/src/plugins/data/server/search/aggs/aggs_service.ts +++ b/src/plugins/data/server/search/aggs/aggs_service.ts @@ -30,6 +30,7 @@ import { TimeRange, } from '../../../common'; import { FieldFormatsStart } from '../../field_formats'; +import { IndexPatternsServiceStart } from '../../index_patterns'; import { AggsSetup, AggsStart } from './types'; /** @internal */ @@ -41,6 +42,7 @@ export interface AggsSetupDependencies { export interface AggsStartDependencies { fieldFormats: FieldFormatsStart; uiSettings: UiSettingsServiceStart; + indexPatterns: IndexPatternsServiceStart; } /** @@ -61,7 +63,7 @@ export class AggsService { return this.aggsCommonService.setup({ registerFunction }); } - public start({ fieldFormats, uiSettings }: AggsStartDependencies): AggsStart { + public start({ fieldFormats, uiSettings, indexPatterns }: AggsStartDependencies): AggsStart { return { asScopedToClient: async (savedObjectsClient: SavedObjectsClientContract) => { const uiSettingsClient = uiSettings.asScopedToClient(savedObjectsClient); @@ -72,8 +74,18 @@ export class AggsService { const getConfig = (key: string): T => { return uiSettingsCache[key]; }; + const isDefaultTimezone = () => getConfig('dateFormat:tz') === 'Browser'; - const { calculateAutoTimeExpression, types } = this.aggsCommonService.start({ getConfig }); + const { + calculateAutoTimeExpression, + getDateMetaByDatatableColumn, + types, + } = this.aggsCommonService.start({ + getConfig, + getIndexPattern: (await indexPatterns.indexPatternsServiceFactory(savedObjectsClient)) + .get, + isDefaultTimezone, + }); const aggTypesDependencies: AggTypesDependencies = { calculateBounds: this.calculateBounds, @@ -87,7 +99,7 @@ export class AggsService { * default timezone, but `isDefault` is not currently offered on the * server, so we need to manually check for the default value. */ - isDefaultTimezone: () => getConfig('dateFormat:tz') === 'Browser', + isDefaultTimezone, }; const typesRegistry = { @@ -109,6 +121,7 @@ export class AggsService { return { calculateAutoTimeExpression, + getDateMetaByDatatableColumn, createAggConfigs: (indexPattern, configStates = [], schemas) => { return new AggConfigs(indexPattern, configStates, { typesRegistry }); }, diff --git a/src/plugins/data/server/search/aggs/mocks.ts b/src/plugins/data/server/search/aggs/mocks.ts index b50e22fe87b7c..be060de73b9ff 100644 --- a/src/plugins/data/server/search/aggs/mocks.ts +++ b/src/plugins/data/server/search/aggs/mocks.ts @@ -68,6 +68,7 @@ export const searchAggsSetupMock = (): AggsSetup => ({ const commonStartMock = (): AggsCommonStart => ({ calculateAutoTimeExpression: getCalculateAutoTimeExpression(getConfig), + getDateMetaByDatatableColumn: jest.fn(), createAggConfigs: jest.fn().mockImplementation((indexPattern, configStates = [], schemas) => { return new AggConfigs(indexPattern, configStates, { typesRegistry: mockAggTypesRegistry(), diff --git a/src/plugins/data/server/search/search_service.ts b/src/plugins/data/server/search/search_service.ts index 0130d3aacc91f..04ee0e95c7f08 100644 --- a/src/plugins/data/server/search/search_service.ts +++ b/src/plugins/data/server/search/search_service.ts @@ -149,7 +149,7 @@ export class SearchService implements Plugin { { fieldFormats, indexPatterns }: SearchServiceStartDependencies ): ISearchStart { return { - aggs: this.aggsService.start({ fieldFormats, uiSettings }), + aggs: this.aggsService.start({ fieldFormats, uiSettings, indexPatterns }), getSearchStrategy: this.getSearchStrategy, search: this.search.bind(this), searchSource: { diff --git a/src/plugins/data/server/server.api.md b/src/plugins/data/server/server.api.md index e5882a6cff809..a3edbbd3844b3 100644 --- a/src/plugins/data/server/server.api.md +++ b/src/plugins/data/server/server.api.md @@ -13,6 +13,7 @@ import { CoreSetup } from 'src/core/server'; import { CoreSetup as CoreSetup_2 } from 'kibana/server'; import { CoreStart } from 'src/core/server'; import { CoreStart as CoreStart_2 } from 'kibana/server'; +import { DatatableColumn } from 'src/plugins/expressions'; import { Duration } from 'moment'; import { ElasticsearchClient } from 'kibana/server'; import { Ensure } from '@kbn/utility-types'; diff --git a/src/plugins/discover/public/application/embeddable/search_embeddable.ts b/src/plugins/discover/public/application/embeddable/search_embeddable.ts index af88cacfcf992..170078076ec6f 100644 --- a/src/plugins/discover/public/application/embeddable/search_embeddable.ts +++ b/src/plugins/discover/public/application/embeddable/search_embeddable.ts @@ -266,6 +266,8 @@ export class SearchEmbeddable } private fetch = async () => { + const searchSessionId = this.input.searchSessionId; + if (!this.searchScope) return; const { searchSource } = this.savedSearch; @@ -292,7 +294,11 @@ export class SearchEmbeddable const description = i18n.translate('discover.embeddable.inspectorRequestDescription', { defaultMessage: 'This request queries Elasticsearch to fetch the data for the search.', }); - const inspectorRequest = this.inspectorAdaptors.requests.start(title, { description }); + + const inspectorRequest = this.inspectorAdaptors.requests.start(title, { + description, + searchSessionId, + }); inspectorRequest.stats(getRequestInspectorStats(searchSource)); searchSource.getSearchRequestBody().then((body: Record) => { inspectorRequest.json(body); @@ -303,6 +309,7 @@ export class SearchEmbeddable // Make the request const resp = await searchSource.fetch({ abortSignal: this.abortController.signal, + sessionId: searchSessionId, }); this.updateOutput({ loading: false, error: undefined }); diff --git a/src/plugins/embeddable/common/types.ts b/src/plugins/embeddable/common/types.ts index 68b842c934de8..2737f2678ff32 100644 --- a/src/plugins/embeddable/common/types.ts +++ b/src/plugins/embeddable/common/types.ts @@ -67,4 +67,9 @@ export type EmbeddableInput = { * Visualization filters used to narrow down results. */ filters?: Filter[]; + + /** + * Search session id to group searches + */ + searchSessionId?: string; }; diff --git a/src/plugins/embeddable/public/lib/embeddables/embeddable.test.tsx b/src/plugins/embeddable/public/lib/embeddables/embeddable.test.tsx index 340d851f3eedf..b020006c0c2bb 100644 --- a/src/plugins/embeddable/public/lib/embeddables/embeddable.test.tsx +++ b/src/plugins/embeddable/public/lib/embeddables/embeddable.test.tsx @@ -25,6 +25,7 @@ import { EmbeddableOutput, EmbeddableInput } from './i_embeddable'; import { ViewMode } from '../types'; import { ContactCardEmbeddable } from '../test_samples/embeddables/contact_card/contact_card_embeddable'; import { FilterableEmbeddable } from '../test_samples/embeddables/filterable_embeddable'; +import type { Filter } from '../../../../data/public'; class TestClass { constructor() {} @@ -79,6 +80,20 @@ test('Embeddable reload is called if lastReloadRequest input time changes', asyn expect(hello.reload).toBeCalledTimes(1); }); +test('Embeddable reload is called if lastReloadRequest input time changed and new input is used', async () => { + const hello = new FilterableEmbeddable({ id: '123', filters: [], lastReloadRequestTime: 0 }); + + const aFilter = ({} as unknown) as Filter; + hello.reload = jest.fn(() => { + // when reload is called embeddable already has new input + expect(hello.getInput().filters).toEqual([aFilter]); + }); + + hello.updateInput({ lastReloadRequestTime: 1, filters: [aFilter] }); + + expect(hello.reload).toBeCalledTimes(1); +}); + test('Embeddable reload is not called if lastReloadRequest input time does not change', async () => { const hello = new FilterableEmbeddable({ id: '123', filters: [], lastReloadRequestTime: 1 }); diff --git a/src/plugins/embeddable/public/lib/embeddables/embeddable.tsx b/src/plugins/embeddable/public/lib/embeddables/embeddable.tsx index 9267d600360cf..c7afc157c1452 100644 --- a/src/plugins/embeddable/public/lib/embeddables/embeddable.tsx +++ b/src/plugins/embeddable/public/lib/embeddables/embeddable.tsx @@ -195,14 +195,15 @@ export abstract class Embeddable< private onResetInput(newInput: TEmbeddableInput) { if (!isEqual(this.input, newInput)) { - if (this.input.lastReloadRequestTime !== newInput.lastReloadRequestTime) { - this.reload(); - } + const oldLastReloadRequestTime = this.input.lastReloadRequestTime; this.input = newInput; this.input$.next(newInput); this.updateOutput({ title: getPanelTitle(this.input, this.output), } as Partial); + if (oldLastReloadRequestTime !== newInput.lastReloadRequestTime) { + this.reload(); + } } } diff --git a/src/plugins/embeddable/public/public.api.md b/src/plugins/embeddable/public/public.api.md index 84dd97c8288fc..00971ed37db3a 100644 --- a/src/plugins/embeddable/public/public.api.md +++ b/src/plugins/embeddable/public/public.api.md @@ -17,6 +17,7 @@ import { CoreSetup as CoreSetup_2 } from 'src/core/public'; import { CoreSetup as CoreSetup_3 } from 'kibana/public'; import { CoreStart as CoreStart_2 } from 'kibana/public'; import * as CSS from 'csstype'; +import { DatatableColumn as DatatableColumn_2 } from 'src/plugins/expressions'; import { EmbeddableStart as EmbeddableStart_2 } from 'src/plugins/embeddable/public/plugin'; import { Ensure } from '@kbn/utility-types'; import { EnvironmentMode } from '@kbn/config'; @@ -425,6 +426,7 @@ export type EmbeddableInput = { timeRange?: TimeRange; query?: Query; filters?: Filter[]; + searchSessionId?: string; }; // Warning: (ae-missing-release-tag) "EmbeddableInstanceConfiguration" is exported by the package, but it is missing a release tag (@alpha, @beta, @public, or @internal) diff --git a/src/plugins/expressions/public/public.api.md b/src/plugins/expressions/public/public.api.md index fe95cf5eb0cda..68a3507bbf166 100644 --- a/src/plugins/expressions/public/public.api.md +++ b/src/plugins/expressions/public/public.api.md @@ -1039,7 +1039,7 @@ export interface Range { // Warning: (ae-missing-release-tag) "ReactExpressionRenderer" is exported by the package, but it is missing a release tag (@alpha, @beta, @public, or @internal) // // @public (undocumented) -export const ReactExpressionRenderer: ({ className, dataAttrs, padding, renderError, expression, onEvent, reload$, ...expressionLoaderOptions }: ReactExpressionRendererProps) => JSX.Element; +export const ReactExpressionRenderer: ({ className, dataAttrs, padding, renderError, expression, onEvent, reload$, debounce, ...expressionLoaderOptions }: ReactExpressionRendererProps) => JSX.Element; // Warning: (ae-missing-release-tag) "ReactExpressionRendererProps" is exported by the package, but it is missing a release tag (@alpha, @beta, @public, or @internal) // @@ -1050,6 +1050,8 @@ export interface ReactExpressionRendererProps extends IExpressionLoaderParams { // (undocumented) dataAttrs?: string[]; // (undocumented) + debounce?: number; + // (undocumented) expression: string | ExpressionAstExpression; // (undocumented) onEvent?: (event: ExpressionRendererEvent) => void; diff --git a/src/plugins/expressions/public/react_expression_renderer.test.tsx b/src/plugins/expressions/public/react_expression_renderer.test.tsx index 7c1711f056d69..052c2a9f6a24a 100644 --- a/src/plugins/expressions/public/react_expression_renderer.test.tsx +++ b/src/plugins/expressions/public/react_expression_renderer.test.tsx @@ -113,6 +113,39 @@ describe('ExpressionRenderer', () => { instance.unmount(); }); + it('waits for debounce period if specified', () => { + jest.useFakeTimers(); + + const refreshSubject = new Subject(); + const loaderUpdate = jest.fn(); + + (ExpressionLoader as jest.Mock).mockImplementation(() => { + return { + render$: new Subject(), + data$: new Subject(), + loading$: new Subject(), + update: loaderUpdate, + destroy: jest.fn(), + }; + }); + + const instance = mount( + + ); + + instance.setProps({ expression: 'abc' }); + + expect(loaderUpdate).toHaveBeenCalledTimes(1); + + act(() => { + jest.runAllTimers(); + }); + + expect(loaderUpdate).toHaveBeenCalledTimes(2); + + instance.unmount(); + }); + it('should display a custom error message if the user provides one and then remove it after successful render', () => { const dataSubject = new Subject(); const data$ = dataSubject.asObservable().pipe(share()); diff --git a/src/plugins/expressions/public/react_expression_renderer.tsx b/src/plugins/expressions/public/react_expression_renderer.tsx index 99d170c96666d..fecebf36ab7e6 100644 --- a/src/plugins/expressions/public/react_expression_renderer.tsx +++ b/src/plugins/expressions/public/react_expression_renderer.tsx @@ -45,6 +45,7 @@ export interface ReactExpressionRendererProps extends IExpressionLoaderParams { * An observable which can be used to re-run the expression without destroying the component */ reload$?: Observable; + debounce?: number; } export type ReactExpressionRendererType = React.ComponentType; @@ -71,6 +72,7 @@ export const ReactExpressionRenderer = ({ expression, onEvent, reload$, + debounce, ...expressionLoaderOptions }: ReactExpressionRendererProps) => { const mountpoint: React.MutableRefObject = useRef(null); @@ -85,12 +87,28 @@ export const ReactExpressionRenderer = ({ const errorRenderHandlerRef: React.MutableRefObject = useRef( null ); + const [debouncedExpression, setDebouncedExpression] = useState(expression); + useEffect(() => { + if (debounce === undefined) { + return; + } + const handler = setTimeout(() => { + setDebouncedExpression(expression); + }, debounce); + + return () => { + clearTimeout(handler); + }; + }, [expression, debounce]); + + const activeExpression = debounce !== undefined ? debouncedExpression : expression; + const waitingForDebounceToComplete = debounce !== undefined && expression !== debouncedExpression; /* eslint-disable react-hooks/exhaustive-deps */ // OK to ignore react-hooks/exhaustive-deps because options update is handled by calling .update() useEffect(() => { const subs: Subscription[] = []; - expressionLoaderRef.current = new ExpressionLoader(mountpoint.current!, expression, { + expressionLoaderRef.current = new ExpressionLoader(mountpoint.current!, activeExpression, { ...expressionLoaderOptions, // react component wrapper provides different // error handling api which is easier to work with from react @@ -146,21 +164,21 @@ export const ReactExpressionRenderer = ({ useEffect(() => { const subscription = reload$?.subscribe(() => { if (expressionLoaderRef.current) { - expressionLoaderRef.current.update(expression, expressionLoaderOptions); + expressionLoaderRef.current.update(activeExpression, expressionLoaderOptions); } }); return () => subscription?.unsubscribe(); - }, [reload$, expression, ...Object.values(expressionLoaderOptions)]); + }, [reload$, activeExpression, ...Object.values(expressionLoaderOptions)]); // Re-fetch data automatically when the inputs change useShallowCompareEffect( () => { if (expressionLoaderRef.current) { - expressionLoaderRef.current.update(expression, expressionLoaderOptions); + expressionLoaderRef.current.update(activeExpression, expressionLoaderOptions); } }, // when expression is changed by reference and when any other loaderOption is changed by reference - [{ expression, ...expressionLoaderOptions }] + [{ activeExpression, ...expressionLoaderOptions }] ); /* eslint-enable react-hooks/exhaustive-deps */ @@ -188,7 +206,9 @@ export const ReactExpressionRenderer = ({ return (
{state.isEmpty && } - {state.isLoading && } + {(state.isLoading || waitingForDebounceToComplete) && ( + + )} {!state.isLoading && state.error && renderError && diff --git a/src/plugins/inspector/common/adapters/request/types.ts b/src/plugins/inspector/common/adapters/request/types.ts index 0a62df7c8d10c..c08c2ef6f706f 100644 --- a/src/plugins/inspector/common/adapters/request/types.ts +++ b/src/plugins/inspector/common/adapters/request/types.ts @@ -49,6 +49,7 @@ export interface Request extends RequestParams { export interface RequestParams { id?: string; description?: string; + searchSessionId?: string; } export interface RequestStatistics { diff --git a/src/plugins/inspector/public/views/requests/components/requests_view.tsx b/src/plugins/inspector/public/views/requests/components/requests_view.tsx index a433ea70dc35c..13575de0c5064 100644 --- a/src/plugins/inspector/public/views/requests/components/requests_view.tsx +++ b/src/plugins/inspector/public/views/requests/components/requests_view.tsx @@ -153,6 +153,21 @@ export class RequestsViewComponent extends Component )} + {this.state.request && this.state.request.searchSessionId && ( + +

+ +

+
+ )} + {this.state.request && } diff --git a/src/plugins/visualizations/public/embeddable/visualize_embeddable.ts b/src/plugins/visualizations/public/embeddable/visualize_embeddable.ts index a810b4b65528f..c12a0f0759018 100644 --- a/src/plugins/visualizations/public/embeddable/visualize_embeddable.ts +++ b/src/plugins/visualizations/public/embeddable/visualize_embeddable.ts @@ -374,6 +374,7 @@ export class VisualizeEmbeddable query: this.input.query, filters: this.input.filters, }, + searchSessionId: this.input.searchSessionId, uiState: this.vis.uiState, inspectorAdapters: this.inspectorAdapters, }; diff --git a/test/interpreter_functional/snapshots/baseline/combined_test2.json b/test/interpreter_functional/snapshots/baseline/combined_test2.json index 550b3b5df12be..4870694e6adbc 100644 --- a/test/interpreter_functional/snapshots/baseline/combined_test2.json +++ b/test/interpreter_functional/snapshots/baseline/combined_test2.json @@ -1 +1 @@ -{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file +{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/combined_test3.json b/test/interpreter_functional/snapshots/baseline/combined_test3.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/baseline/combined_test3.json +++ b/test/interpreter_functional/snapshots/baseline/combined_test3.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/final_output_test.json b/test/interpreter_functional/snapshots/baseline/final_output_test.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/baseline/final_output_test.json +++ b/test/interpreter_functional/snapshots/baseline/final_output_test.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/metric_all_data.json b/test/interpreter_functional/snapshots/baseline/metric_all_data.json index cf488ac7f3ffa..dd779800cd452 100644 --- a/test/interpreter_functional/snapshots/baseline/metric_all_data.json +++ b/test/interpreter_functional/snapshots/baseline/metric_all_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":2,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":2,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/metric_multi_metric_data.json b/test/interpreter_functional/snapshots/baseline/metric_multi_metric_data.json index 8c272901c4e84..992d667fdce9f 100644 --- a/test/interpreter_functional/snapshots/baseline/metric_multi_metric_data.json +++ b/test/interpreter_functional/snapshots/baseline/metric_multi_metric_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/metric_percentage_mode.json b/test/interpreter_functional/snapshots/baseline/metric_percentage_mode.json index abc0d3a446987..031c9f9ea5504 100644 --- a/test/interpreter_functional/snapshots/baseline/metric_percentage_mode.json +++ b/test/interpreter_functional/snapshots/baseline/metric_percentage_mode.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":1000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":true,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":1000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":true,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/metric_single_metric_data.json b/test/interpreter_functional/snapshots/baseline/metric_single_metric_data.json index 1809df5e709f0..8c6fde201c8f1 100644 --- a/test/interpreter_functional/snapshots/baseline/metric_single_metric_data.json +++ b/test/interpreter_functional/snapshots/baseline/metric_single_metric_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/partial_test_1.json b/test/interpreter_functional/snapshots/baseline/partial_test_1.json index ec32b07ed9f2e..14c8428c6d432 100644 --- a/test/interpreter_functional/snapshots/baseline/partial_test_1.json +++ b/test/interpreter_functional/snapshots/baseline/partial_test_1.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/partial_test_2.json b/test/interpreter_functional/snapshots/baseline/partial_test_2.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/baseline/partial_test_2.json +++ b/test/interpreter_functional/snapshots/baseline/partial_test_2.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/partial_test_3.json b/test/interpreter_functional/snapshots/baseline/partial_test_3.json index 09602eca4abf2..595127526156e 100644 --- a/test/interpreter_functional/snapshots/baseline/partial_test_3.json +++ b/test/interpreter_functional/snapshots/baseline/partial_test_3.json @@ -1 +1 @@ -{"as":"visualization","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"bucket":{"accessor":0},"metric":{"accessor":1,"format":{"id":"number"}}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"region_map"}} \ No newline at end of file +{"as":"visualization","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"bucket":{"accessor":0},"metric":{"accessor":1,"format":{"id":"number"}}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"region_map"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/step_output_test2.json b/test/interpreter_functional/snapshots/baseline/step_output_test2.json index 550b3b5df12be..4870694e6adbc 100644 --- a/test/interpreter_functional/snapshots/baseline/step_output_test2.json +++ b/test/interpreter_functional/snapshots/baseline/step_output_test2.json @@ -1 +1 @@ -{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file +{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/step_output_test3.json b/test/interpreter_functional/snapshots/baseline/step_output_test3.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/baseline/step_output_test3.json +++ b/test/interpreter_functional/snapshots/baseline/step_output_test3.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/tagcloud_all_data.json b/test/interpreter_functional/snapshots/baseline/tagcloud_all_data.json index 071172c698ad7..073fca760b9a2 100644 --- a/test/interpreter_functional/snapshots/baseline/tagcloud_all_data.json +++ b/test/interpreter_functional/snapshots/baseline/tagcloud_all_data.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/tagcloud_fontsize.json b/test/interpreter_functional/snapshots/baseline/tagcloud_fontsize.json index ad38bb28b3329..93f8d8a27d233 100644 --- a/test/interpreter_functional/snapshots/baseline/tagcloud_fontsize.json +++ b/test/interpreter_functional/snapshots/baseline/tagcloud_fontsize.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":40,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":20,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":40,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":20,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/tagcloud_metric_data.json b/test/interpreter_functional/snapshots/baseline/tagcloud_metric_data.json index 997285adfe5f4..e8c47efdbe622 100644 --- a/test/interpreter_functional/snapshots/baseline/tagcloud_metric_data.json +++ b/test/interpreter_functional/snapshots/baseline/tagcloud_metric_data.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/baseline/tagcloud_options.json b/test/interpreter_functional/snapshots/baseline/tagcloud_options.json index 10e23d860637c..38683082975f8 100644 --- a/test/interpreter_functional/snapshots/baseline/tagcloud_options.json +++ b/test/interpreter_functional/snapshots/baseline/tagcloud_options.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"multiple","scale":"log","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"multiple","scale":"log","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/combined_test2.json b/test/interpreter_functional/snapshots/session/combined_test2.json index 550b3b5df12be..4870694e6adbc 100644 --- a/test/interpreter_functional/snapshots/session/combined_test2.json +++ b/test/interpreter_functional/snapshots/session/combined_test2.json @@ -1 +1 @@ -{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file +{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/combined_test3.json b/test/interpreter_functional/snapshots/session/combined_test3.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/session/combined_test3.json +++ b/test/interpreter_functional/snapshots/session/combined_test3.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/final_output_test.json b/test/interpreter_functional/snapshots/session/final_output_test.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/session/final_output_test.json +++ b/test/interpreter_functional/snapshots/session/final_output_test.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/metric_all_data.json b/test/interpreter_functional/snapshots/session/metric_all_data.json index cf488ac7f3ffa..dd779800cd452 100644 --- a/test/interpreter_functional/snapshots/session/metric_all_data.json +++ b/test/interpreter_functional/snapshots/session/metric_all_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":2,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":2,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/metric_multi_metric_data.json b/test/interpreter_functional/snapshots/session/metric_multi_metric_data.json index 8c272901c4e84..992d667fdce9f 100644 --- a/test/interpreter_functional/snapshots/session/metric_multi_metric_data.json +++ b/test/interpreter_functional/snapshots/session/metric_multi_metric_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/metric_percentage_mode.json b/test/interpreter_functional/snapshots/session/metric_percentage_mode.json index abc0d3a446987..031c9f9ea5504 100644 --- a/test/interpreter_functional/snapshots/session/metric_percentage_mode.json +++ b/test/interpreter_functional/snapshots/session/metric_percentage_mode.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":1000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":true,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":1000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":true,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/metric_single_metric_data.json b/test/interpreter_functional/snapshots/session/metric_single_metric_data.json index 1809df5e709f0..8c6fde201c8f1 100644 --- a/test/interpreter_functional/snapshots/session/metric_single_metric_data.json +++ b/test/interpreter_functional/snapshots/session/metric_single_metric_data.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"metrics":[{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"},{"id":"col-2-1","meta":{"field":"bytes","index":"logstash-*","params":{"id":"bytes","params":null},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{"field":"bytes"},"schema":"metric","type":"max"},"type":"number"},"name":"Max bytes"}],"rows":[{"col-0-2":"200","col-1-1":12891,"col-2-1":19986},{"col-0-2":"404","col-1-1":696,"col-2-1":19881},{"col-0-2":"503","col-1-1":417,"col-2-1":0}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/partial_test_1.json b/test/interpreter_functional/snapshots/session/partial_test_1.json index ec32b07ed9f2e..14c8428c6d432 100644 --- a/test/interpreter_functional/snapshots/session/partial_test_1.json +++ b/test/interpreter_functional/snapshots/session/partial_test_1.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/partial_test_2.json b/test/interpreter_functional/snapshots/session/partial_test_2.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/session/partial_test_2.json +++ b/test/interpreter_functional/snapshots/session/partial_test_2.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/partial_test_3.json b/test/interpreter_functional/snapshots/session/partial_test_3.json index 09602eca4abf2..595127526156e 100644 --- a/test/interpreter_functional/snapshots/session/partial_test_3.json +++ b/test/interpreter_functional/snapshots/session/partial_test_3.json @@ -1 +1 @@ -{"as":"visualization","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"bucket":{"accessor":0},"metric":{"accessor":1,"format":{"id":"number"}}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"region_map"}} \ No newline at end of file +{"as":"visualization","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"bucket":{"accessor":0},"metric":{"accessor":1,"format":{"id":"number"}}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"region_map"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/step_output_test2.json b/test/interpreter_functional/snapshots/session/step_output_test2.json index 550b3b5df12be..4870694e6adbc 100644 --- a/test/interpreter_functional/snapshots/session/step_output_test2.json +++ b/test/interpreter_functional/snapshots/session/step_output_test2.json @@ -1 +1 @@ -{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file +{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/step_output_test3.json b/test/interpreter_functional/snapshots/session/step_output_test3.json index 59de1f285799b..2aa601a8d3631 100644 --- a/test/interpreter_functional/snapshots/session/step_output_test3.json +++ b/test/interpreter_functional/snapshots/session/step_output_test3.json @@ -1 +1 @@ -{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file +{"as":"metric_vis","type":"render","value":{"params":{"listenOnChange":true},"visConfig":{"dimensions":{"bucket":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"metrics":[{"accessor":1,"format":{"id":"number","params":{}},"type":"vis_dimension"}]},"metric":{"colorSchema":"Green to Red","colorsRange":[{"from":0,"to":10000,"type":"range"}],"invertColors":false,"labels":{"show":true},"metricColorMode":"None","percentageMode":false,"style":{"bgColor":false,"bgFill":"#000","fontSize":60,"labelColor":false,"subText":""},"useRanges":false}},"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visType":"metric"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/tagcloud_all_data.json b/test/interpreter_functional/snapshots/session/tagcloud_all_data.json index 071172c698ad7..073fca760b9a2 100644 --- a/test/interpreter_functional/snapshots/session/tagcloud_all_data.json +++ b/test/interpreter_functional/snapshots/session/tagcloud_all_data.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/tagcloud_fontsize.json b/test/interpreter_functional/snapshots/session/tagcloud_fontsize.json index ad38bb28b3329..93f8d8a27d233 100644 --- a/test/interpreter_functional/snapshots/session/tagcloud_fontsize.json +++ b/test/interpreter_functional/snapshots/session/tagcloud_fontsize.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":40,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":20,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":40,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":20,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/tagcloud_metric_data.json b/test/interpreter_functional/snapshots/session/tagcloud_metric_data.json index 997285adfe5f4..e8c47efdbe622 100644 --- a/test/interpreter_functional/snapshots/session/tagcloud_metric_data.json +++ b/test/interpreter_functional/snapshots/session/tagcloud_metric_data.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"single","scale":"linear","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/test/interpreter_functional/snapshots/session/tagcloud_options.json b/test/interpreter_functional/snapshots/session/tagcloud_options.json index 10e23d860637c..38683082975f8 100644 --- a/test/interpreter_functional/snapshots/session/tagcloud_options.json +++ b/test/interpreter_functional/snapshots/session/tagcloud_options.json @@ -1 +1 @@ -{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"multiple","scale":"log","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file +{"as":"tagloud_vis","type":"render","value":{"visData":{"columns":[{"id":"col-0-2","meta":{"field":"response.raw","index":"logstash-*","params":{"id":"terms","params":{"id":"string","missingBucketLabel":"Missing","otherBucketLabel":"Other"}},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"2","indexPatternId":"logstash-*","params":{"field":"response.raw","missingBucket":false,"missingBucketLabel":"Missing","order":"desc","orderBy":"1","otherBucket":false,"otherBucketLabel":"Other","size":4},"schema":"segment","type":"terms"},"type":"string"},"name":"response.raw: Descending"},{"id":"col-1-1","meta":{"field":null,"index":"logstash-*","params":{"id":"number"},"source":"esaggs","sourceParams":{"appliedTimeRange":null,"enabled":true,"id":"1","indexPatternId":"logstash-*","params":{},"schema":"metric","type":"count"},"type":"number"},"name":"Count"}],"rows":[{"col-0-2":"200","col-1-1":12891},{"col-0-2":"404","col-1-1":696},{"col-0-2":"503","col-1-1":417}],"type":"datatable"},"visParams":{"bucket":{"accessor":1,"format":{"id":"string","params":{}},"type":"vis_dimension"},"maxFontSize":72,"metric":{"accessor":0,"format":{"id":"string","params":{}},"type":"vis_dimension"},"minFontSize":18,"orientation":"multiple","scale":"log","showLabel":true},"visType":"tagcloud"}} \ No newline at end of file diff --git a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_dashboard.ts b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_dashboard.ts index a8edf862ab256..d8540c3f3efd7 100644 --- a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_dashboard.ts +++ b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_dashboard.ts @@ -26,7 +26,7 @@ Given(`a user browses the APM UI application for RUM Data`, () => { }); Then(`should have correct client metrics`, () => { - const metrics = ['4 ms', '58 ms', '55']; + const metrics = ['80 ms', '4 ms', '76 ms', '55']; verifyClientMetrics(metrics, true); }); diff --git a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_filters.ts b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_filters.ts index 5c2109bb518c2..88287286c66c5 100644 --- a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_filters.ts +++ b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/csm_filters.ts @@ -56,7 +56,9 @@ Then(/^it filters the client metrics "([^"]*)"$/, (filterName) => { cy.get('.euiStat__title-isLoading').should('not.be.visible'); const data = - filterName === 'os' ? ['5 ms', '64 ms', '8'] : ['4 ms', '55 ms', '28']; + filterName === 'os' + ? ['82 ms', '5 ms', '77 ms', '8'] + : ['75 ms', '4 ms', '71 ms', '28']; verifyClientMetrics(data, true); diff --git a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/percentile_select.ts b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/percentile_select.ts index 314254883b2fd..44802bbce6208 100644 --- a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/percentile_select.ts +++ b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/percentile_select.ts @@ -16,7 +16,7 @@ When('the user changes the selected percentile', () => { }); Then(`it displays client metric related to that percentile`, () => { - const metrics = ['14 ms', '131 ms', '55']; + const metrics = ['165 ms', '14 ms', '151 ms', '55']; verifyClientMetrics(metrics, false); diff --git a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/service_name_filter.ts b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/service_name_filter.ts index 20c6a3fb72aa9..609d0d18f5bc8 100644 --- a/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/service_name_filter.ts +++ b/x-pack/plugins/apm/e2e/cypress/support/step_definitions/csm/service_name_filter.ts @@ -15,7 +15,7 @@ When('the user changes the selected service name', () => { }); Then(`it displays relevant client metrics`, () => { - const metrics = ['4 ms', '58 ms', '55']; + const metrics = ['80 ms', '4 ms', '76 ms', '55']; verifyClientMetrics(metrics, false); }); diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/ClientMetrics/index.tsx b/x-pack/plugins/apm/public/components/app/RumDashboard/ClientMetrics/index.tsx index 0b4dcea5d12e0..b6924b9552699 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/ClientMetrics/index.tsx +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/ClientMetrics/index.tsx @@ -7,7 +7,13 @@ import * as React from 'react'; import numeral from '@elastic/numeral'; import styled from 'styled-components'; import { useContext, useEffect } from 'react'; -import { EuiFlexGroup, EuiFlexItem, EuiStat, EuiToolTip } from '@elastic/eui'; +import { + EuiFlexGroup, + EuiFlexItem, + EuiStat, + EuiToolTip, + EuiIconTip, +} from '@elastic/eui'; import { useFetcher } from '../../../../hooks/useFetcher'; import { I18LABELS } from '../translations'; import { useUxQuery } from '../hooks/useUxQuery'; @@ -70,11 +76,35 @@ export function ClientMetrics() { return ( + + + {I18LABELS.totalPageLoad} + + + } + isLoading={status !== 'success'} + /> + + {I18LABELS.backEnd} + + + } isLoading={status !== 'success'} /> @@ -82,7 +112,15 @@ export function ClientMetrics() { + {I18LABELS.frontEnd} + + + } isLoading={status !== 'success'} /> diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/RumDashboard.tsx b/x-pack/plugins/apm/public/components/app/RumDashboard/RumDashboard.tsx index b19adb12d02d4..e4e9109f007e7 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/RumDashboard.tsx +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/RumDashboard.tsx @@ -36,8 +36,7 @@ export function RumDashboard() {

- {I18LABELS.pageLoadDuration} ( - {getPercentileLabel(percentile!)}) + {I18LABELS.pageLoad} ({getPercentileLabel(percentile!)})

diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/KeyUXMetrics.tsx b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/KeyUXMetrics.tsx index e91f129195366..c7fe8e885020a 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/KeyUXMetrics.tsx +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/KeyUXMetrics.tsx @@ -5,15 +5,20 @@ */ import React from 'react'; -import { EuiFlexItem, EuiStat, EuiFlexGroup } from '@elastic/eui'; +import { EuiFlexItem, EuiStat, EuiFlexGroup, EuiIconTip } from '@elastic/eui'; import numeral from '@elastic/numeral'; import { DATA_UNDEFINED_LABEL, FCP_LABEL, + FCP_TOOLTIP, LONGEST_LONG_TASK, + LONGEST_LONG_TASK_TOOLTIP, NO_OF_LONG_TASK, + NO_OF_LONG_TASK_TOOLTIP, SUM_LONG_TASKS, + SUM_LONG_TASKS_TOOLTIP, TBT_LABEL, + TBT_TOOLTIP, } from './translations'; import { useFetcher } from '../../../../hooks/useFetcher'; import { useUxQuery } from '../hooks/useUxQuery'; @@ -70,7 +75,12 @@ export function KeyUXMetrics({ data, loading }: Props) { + {FCP_LABEL} + + + } isLoading={loading} />
@@ -78,7 +88,12 @@ export function KeyUXMetrics({ data, loading }: Props) { + {TBT_LABEL} + + + } isLoading={loading} /> @@ -90,7 +105,15 @@ export function KeyUXMetrics({ data, loading }: Props) { ? numeral(longTaskData?.noOfLongTasks).format('0,0') : DATA_UNDEFINED_LABEL } - description={NO_OF_LONG_TASK} + description={ + <> + {NO_OF_LONG_TASK} + + + } isLoading={status !== 'success'} /> @@ -98,7 +121,15 @@ export function KeyUXMetrics({ data, loading }: Props) { + {LONGEST_LONG_TASK} + + + } isLoading={status !== 'success'} /> @@ -106,7 +137,15 @@ export function KeyUXMetrics({ data, loading }: Props) { + {SUM_LONG_TASKS} + + + } isLoading={status !== 'success'} /> diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/__tests__/KeyUXMetrics.test.tsx b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/__tests__/KeyUXMetrics.test.tsx index 329339deb2f89..3a6323a747a70 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/__tests__/KeyUXMetrics.test.tsx +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/__tests__/KeyUXMetrics.test.tsx @@ -19,7 +19,7 @@ describe('KeyUXMetrics', () => { status: fetcherHook.FETCH_STATUS.SUCCESS, refetch: jest.fn(), }); - const { getByText } = render( + const { getAllByText } = render( { /> ); - expect(getByText('Longest long task duration 271 ms')).toBeInTheDocument(); - expect(getByText('Total long tasks duration 520 ms')).toBeInTheDocument(); - expect(getByText('No. of long tasks 3')).toBeInTheDocument(); - expect(getByText('Total blocking time 271 ms')).toBeInTheDocument(); - expect(getByText('First contentful paint 1.27 s')).toBeInTheDocument(); + const checkText = (text: string) => { + return (content: any, node: any) => { + return node?.textContent?.includes(text); + }; + }; + + expect( + getAllByText(checkText('Longest long task duration271 ms'))[0] + ).toBeInTheDocument(); + expect( + getAllByText(checkText('Total long tasks duration520 ms'))[0] + ).toBeInTheDocument(); + expect( + getAllByText(checkText('No. of long tasks3'))[0] + ).toBeInTheDocument(); + expect( + getAllByText(checkText('Total blocking time271 ms'))[0] + ).toBeInTheDocument(); + expect( + getAllByText(checkText('First contentful paint1.27 s'))[0] + ).toBeInTheDocument(); }); }); diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/translations.ts b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/translations.ts index 5920dc92f558d..3795f2f102237 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/translations.ts +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/UXMetrics/translations.ts @@ -18,10 +18,26 @@ export const FCP_LABEL = i18n.translate('xpack.apm.rum.coreVitals.fcp', { defaultMessage: 'First contentful paint', }); +export const FCP_TOOLTIP = i18n.translate( + 'xpack.apm.rum.coreVitals.fcpTooltip', + { + defaultMessage: + 'First contentful paint (FCP) focusses on the initial rendering and measures the time from when the page starts loading to when any part of the page’s content is displayed on the screen.', + } +); + export const TBT_LABEL = i18n.translate('xpack.apm.rum.coreVitals.tbt', { defaultMessage: 'Total blocking time', }); +export const TBT_TOOLTIP = i18n.translate( + 'xpack.apm.rum.coreVitals.tbtTooltip', + { + defaultMessage: + 'Total blocking time (TBT) is the sum of the blocking time (duration above 50 ms) for each long task that occurs between the First contentful paint and the time when the transaction is completed.', + } +); + export const NO_OF_LONG_TASK = i18n.translate( 'xpack.apm.rum.uxMetrics.noOfLongTasks', { @@ -29,6 +45,14 @@ export const NO_OF_LONG_TASK = i18n.translate( } ); +export const NO_OF_LONG_TASK_TOOLTIP = i18n.translate( + 'xpack.apm.rum.uxMetrics.noOfLongTasksTooltip', + { + defaultMessage: + 'The number of long tasks, a long task is defined as any user activity or browser task that monopolizes the UI thread for extended periods (greater than 50 milliseconds) and blocks other critical tasks (frame rate or input latency) from being executed.', + } +); + export const LONGEST_LONG_TASK = i18n.translate( 'xpack.apm.rum.uxMetrics.longestLongTasks', { @@ -36,6 +60,14 @@ export const LONGEST_LONG_TASK = i18n.translate( } ); +export const LONGEST_LONG_TASK_TOOLTIP = i18n.translate( + 'xpack.apm.rum.uxMetrics.longestLongTasksTooltip', + { + defaultMessage: + 'The duration of the longest long task, a long task is defined as any user activity or browser task that monopolizes the UI thread for extended periods (greater than 50 milliseconds) and blocks other critical tasks (frame rate or input latency) from being executed.', + } +); + export const SUM_LONG_TASKS = i18n.translate( 'xpack.apm.rum.uxMetrics.sumLongTasks', { @@ -43,6 +75,14 @@ export const SUM_LONG_TASKS = i18n.translate( } ); +export const SUM_LONG_TASKS_TOOLTIP = i18n.translate( + 'xpack.apm.rum.uxMetrics.sumLongTasksTooltip', + { + defaultMessage: + 'The total duration of long tasks, a long task is defined as any user activity or browser task that monopolizes the UI thread for extended periods (greater than 50 milliseconds) and blocks other critical tasks (frame rate or input latency) from being executed.', + } +); + export const getPercentileLabel = (value: number) => { if (value === 50) return I18LABELS.median; diff --git a/x-pack/plugins/apm/public/components/app/RumDashboard/translations.ts b/x-pack/plugins/apm/public/components/app/RumDashboard/translations.ts index b7ecfc08db13b..75df1381d8a1d 100644 --- a/x-pack/plugins/apm/public/components/app/RumDashboard/translations.ts +++ b/x-pack/plugins/apm/public/components/app/RumDashboard/translations.ts @@ -10,6 +10,9 @@ export const I18LABELS = { dataMissing: i18n.translate('xpack.apm.rum.dashboard.dataMissing', { defaultMessage: 'N/A', }), + totalPageLoad: i18n.translate('xpack.apm.rum.dashboard.totalPageLoad', { + defaultMessage: 'Total', + }), backEnd: i18n.translate('xpack.apm.rum.dashboard.backend', { defaultMessage: 'Backend', }), @@ -34,6 +37,9 @@ export const I18LABELS = { defaultMessage: 'Page load duration', } ), + pageLoad: i18n.translate('xpack.apm.rum.dashboard.pageLoad.label', { + defaultMessage: 'Page load', + }), pageLoadDistribution: i18n.translate( 'xpack.apm.rum.dashboard.pageLoadDistribution.label', { @@ -156,6 +162,21 @@ export const I18LABELS = { noData: i18n.translate('xpack.apm.ux.visitorBreakdown.noData', { defaultMessage: 'No data.', }), + // Helper tooltips + totalPageLoadTooltip: i18n.translate( + 'xpack.apm.rum.dashboard.tooltips.totalPageLoad', + { + defaultMessage: 'Total represents the full page load duration', + } + ), + frontEndTooltip: i18n.translate('xpack.apm.rum.dashboard.tooltips.frontEnd', { + defaultMessage: + 'Frontend time represents the total page load duration minus the backend time', + }), + backEndTooltip: i18n.translate('xpack.apm.rum.dashboard.tooltips.backEnd', { + defaultMessage: + 'Backend time represents time to first byte (TTFB), which is when the first response packet is received after the request has been made', + }), }; export const VisitorBreakdownLabel = i18n.translate( diff --git a/x-pack/plugins/apm/server/lib/rum_client/__snapshots__/queries.test.ts.snap b/x-pack/plugins/apm/server/lib/rum_client/__snapshots__/queries.test.ts.snap index 53dcd2f469148..b89c46f6e3fc5 100644 --- a/x-pack/plugins/apm/server/lib/rum_client/__snapshots__/queries.test.ts.snap +++ b/x-pack/plugins/apm/server/lib/rum_client/__snapshots__/queries.test.ts.snap @@ -22,9 +22,9 @@ Object { ], }, }, - "domInteractive": Object { + "totalPageLoadDuration": Object { "percentiles": Object { - "field": "transaction.marks.agent.domInteractive", + "field": "transaction.duration.us", "hdr": Object { "number_of_significant_value_digits": 3, }, diff --git a/x-pack/plugins/apm/server/lib/rum_client/get_client_metrics.ts b/x-pack/plugins/apm/server/lib/rum_client/get_client_metrics.ts index da65e69e7eb7c..6685a60f84f05 100644 --- a/x-pack/plugins/apm/server/lib/rum_client/get_client_metrics.ts +++ b/x-pack/plugins/apm/server/lib/rum_client/get_client_metrics.ts @@ -8,8 +8,8 @@ import { getRumPageLoadTransactionsProjection } from '../../projections/rum_page import { mergeProjection } from '../../projections/util/merge_projection'; import { Setup, SetupTimeRange } from '../helpers/setup_request'; import { - TRANSACTION_DOM_INTERACTIVE, TRANSACTION_TIME_TO_FIRST_BYTE, + TRANSACTION_DURATION, } from '../../../common/elasticsearch_fieldnames'; export async function getClientMetrics({ @@ -37,18 +37,18 @@ export async function getClientMetrics({ exists: { field: 'transaction.marks.navigationTiming.fetchStart' }, }, aggs: { - backEnd: { + totalPageLoadDuration: { percentiles: { - field: TRANSACTION_TIME_TO_FIRST_BYTE, + field: TRANSACTION_DURATION, percents: [percentile], hdr: { number_of_significant_value_digits: 3, }, }, }, - domInteractive: { + backEnd: { percentiles: { - field: TRANSACTION_DOM_INTERACTIVE, + field: TRANSACTION_TIME_TO_FIRST_BYTE, percents: [percentile], hdr: { number_of_significant_value_digits: 3, @@ -64,17 +64,19 @@ export async function getClientMetrics({ const { apmEventClient } = setup; const response = await apmEventClient.search(params); const { - hasFetchStartField: { backEnd, domInteractive }, + hasFetchStartField: { backEnd, totalPageLoadDuration }, } = response.aggregations!; const pkey = percentile.toFixed(1); - // Divide by 1000 to convert ms into seconds + const totalPageLoadDurationValue = totalPageLoadDuration.values[pkey] ?? 0; + const totalPageLoadDurationValueMs = totalPageLoadDurationValue / 1000; // Microseconds to milliseconds + const backendValue = backEnd.values[pkey] ?? 0; + return { pageViews: { value: response.hits.total.value ?? 0 }, - backEnd: { value: backEnd.values[pkey] || 0 }, - frontEnd: { - value: (domInteractive.values[pkey] || 0) - (backEnd.values[pkey] || 0), - }, + totalPageLoadDuration: { value: totalPageLoadDurationValueMs }, + backEnd: { value: backendValue }, + frontEnd: { value: totalPageLoadDurationValueMs - backendValue }, }; } diff --git a/x-pack/plugins/ingest_manager/server/services/epm/packages/get.ts b/x-pack/plugins/ingest_manager/server/services/epm/packages/get.ts index 2cf94e9c16079..cd0dcba7b97b2 100644 --- a/x-pack/plugins/ingest_manager/server/services/epm/packages/get.ts +++ b/x-pack/plugins/ingest_manager/server/services/epm/packages/get.ts @@ -86,7 +86,7 @@ export async function getPackageKeysByStatus( savedObjectsClient: SavedObjectsClientContract, status: InstallationStatus ) { - const allPackages = await getPackages({ savedObjectsClient }); + const allPackages = await getPackages({ savedObjectsClient, experimental: true }); return allPackages.reduce>((acc, pkg) => { if (pkg.status === status) { if (pkg.status === InstallationStatus.installed) { diff --git a/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx b/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx index 5e5e9cda954ee..63ee02ac0404d 100644 --- a/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx +++ b/x-pack/plugins/lens/public/editor_frame_service/editor_frame/suggestion_panel.tsx @@ -32,16 +32,11 @@ import { ReactExpressionRendererType, } from '../../../../../../src/plugins/expressions/public'; import { prependDatasourceExpression } from './expression_helpers'; -import { debouncedComponent } from '../../debounced_component'; import { trackUiEvent, trackSuggestionEvent } from '../../lens_ui_telemetry'; import { DataPublicPluginStart } from '../../../../../../src/plugins/data/public'; const MAX_SUGGESTIONS_DISPLAYED = 5; -// TODO: Remove this when upstream fix is merged https://github.com/elastic/eui/issues/2329 -// eslint-disable-next-line -const EuiPanelFixed = EuiPanel as React.ComponentType; - export interface SuggestionPanelProps { activeDatasourceId: string | null; datasourceMap: Record; @@ -82,6 +77,7 @@ const PreviewRenderer = ({ className="lnsSuggestionPanel__expressionRenderer" padding="s" expression={expression} + debounce={2000} renderError={() => { return (
@@ -104,8 +100,6 @@ const PreviewRenderer = ({ ); }; -const DebouncedPreviewRenderer = debouncedComponent(PreviewRenderer, 2000); - const SuggestionPreview = ({ preview, ExpressionRenderer: ExpressionRendererComponent, @@ -126,7 +120,7 @@ const SuggestionPreview = ({ return (
- {preview.expression ? ( - {preview.title} )} - +
); diff --git a/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.test.tsx b/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.test.tsx index 3e05d4ddfbc20..9dc59eacd40d3 100644 --- a/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.test.tsx +++ b/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.test.tsx @@ -172,6 +172,7 @@ describe('embeddable', () => { timeRange, query, filters, + searchSessionId: 'searchSessionId', }); expect(expressionRenderer).toHaveBeenCalledTimes(2); @@ -182,7 +183,13 @@ describe('embeddable', () => { const query: Query = { language: 'kquery', query: '' }; const filters: Filter[] = [{ meta: { alias: 'test', negate: false, disabled: false } }]; - const input = { savedObjectId: '123', timeRange, query, filters } as LensEmbeddableInput; + const input = { + savedObjectId: '123', + timeRange, + query, + filters, + searchSessionId: 'searchSessionId', + } as LensEmbeddableInput; const embeddable = new Embeddable( { @@ -214,6 +221,8 @@ describe('embeddable', () => { filters, }) ); + + expect(expressionRenderer.mock.calls[0][0].searchSessionId).toBe(input.searchSessionId); }); it('should merge external context with query and filters of the saved object', async () => { diff --git a/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.tsx b/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.tsx index d245b7f2fcde4..10c243a272138 100644 --- a/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.tsx +++ b/x-pack/plugins/lens/public/editor_frame_service/embeddable/embeddable.tsx @@ -177,6 +177,7 @@ export class Embeddable ExpressionRenderer={this.expressionRenderer} expression={this.expression || null} searchContext={this.getMergedSearchContext()} + searchSessionId={this.input.searchSessionId} handleEvent={this.handleEvent} />, domNode diff --git a/x-pack/plugins/lens/public/editor_frame_service/embeddable/expression_wrapper.tsx b/x-pack/plugins/lens/public/editor_frame_service/embeddable/expression_wrapper.tsx index 4fb0630a305e7..13376e56e2144 100644 --- a/x-pack/plugins/lens/public/editor_frame_service/embeddable/expression_wrapper.tsx +++ b/x-pack/plugins/lens/public/editor_frame_service/embeddable/expression_wrapper.tsx @@ -19,6 +19,7 @@ export interface ExpressionWrapperProps { ExpressionRenderer: ReactExpressionRendererType; expression: string | null; searchContext: ExecutionContextSearch; + searchSessionId?: string; handleEvent: (event: ExpressionRendererEvent) => void; } @@ -27,6 +28,7 @@ export function ExpressionWrapper({ expression, searchContext, handleEvent, + searchSessionId, }: ExpressionWrapperProps) { return ( @@ -51,6 +53,7 @@ export function ExpressionWrapper({ padding="m" expression={expression} searchContext={searchContext} + searchSessionId={searchSessionId} renderError={(errorMessage, error) => (
diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/indexpattern.test.ts b/x-pack/plugins/lens/public/indexpattern_datasource/indexpattern.test.ts index 900cd02622aaf..77dc6f97fb236 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/indexpattern.test.ts +++ b/x-pack/plugins/lens/public/indexpattern_datasource/indexpattern.test.ts @@ -319,10 +319,10 @@ describe('IndexPattern Data Source', () => { "1", ], "metricsAtAllLevels": Array [ - true, + false, ], "partialRows": Array [ - true, + false, ], "timeFields": Array [ "timestamp", @@ -334,7 +334,7 @@ describe('IndexPattern Data Source', () => { Object { "arguments": Object { "idMap": Array [ - "{\\"col--1-col1\\":{\\"label\\":\\"Count of records\\",\\"dataType\\":\\"number\\",\\"isBucketed\\":false,\\"sourceField\\":\\"Records\\",\\"operationType\\":\\"count\\",\\"id\\":\\"col1\\"},\\"col-2-col2\\":{\\"label\\":\\"Date\\",\\"dataType\\":\\"date\\",\\"isBucketed\\":true,\\"operationType\\":\\"date_histogram\\",\\"sourceField\\":\\"timestamp\\",\\"params\\":{\\"interval\\":\\"1d\\"},\\"id\\":\\"col2\\"}}", + "{\\"col-0-col1\\":{\\"label\\":\\"Count of records\\",\\"dataType\\":\\"number\\",\\"isBucketed\\":false,\\"sourceField\\":\\"Records\\",\\"operationType\\":\\"count\\",\\"id\\":\\"col1\\"},\\"col-1-col2\\":{\\"label\\":\\"Date\\",\\"dataType\\":\\"date\\",\\"isBucketed\\":true,\\"operationType\\":\\"date_histogram\\",\\"sourceField\\":\\"timestamp\\",\\"params\\":{\\"interval\\":\\"1d\\"},\\"id\\":\\"col2\\"}}", ], }, "function": "lens_rename_columns", @@ -392,6 +392,58 @@ describe('IndexPattern Data Source', () => { expect(ast.chain[0].arguments.timeFields).toEqual(['timestamp', 'another_datefield']); }); + it('should rename the output from esaggs when using flat query', () => { + const queryBaseState: IndexPatternBaseState = { + currentIndexPatternId: '1', + layers: { + first: { + indexPatternId: '1', + columnOrder: ['bucket1', 'bucket2', 'metric'], + columns: { + metric: { + label: 'Count of records', + dataType: 'number', + isBucketed: false, + sourceField: 'Records', + operationType: 'count', + }, + bucket1: { + label: 'Date', + dataType: 'date', + isBucketed: true, + operationType: 'date_histogram', + sourceField: 'timestamp', + params: { + interval: '1d', + }, + }, + bucket2: { + label: 'Terms', + dataType: 'string', + isBucketed: true, + operationType: 'terms', + sourceField: 'geo.src', + params: { + orderBy: { type: 'alphabetical' }, + orderDirection: 'asc', + size: 10, + }, + }, + }, + }, + }, + }; + + const state = enrichBaseState(queryBaseState); + const ast = indexPatternDatasource.toExpression(state, 'first') as Ast; + expect(ast.chain[0].arguments.metricsAtAllLevels).toEqual([false]); + expect(JSON.parse(ast.chain[1].arguments.idMap[0] as string)).toEqual({ + 'col-0-bucket1': expect.any(Object), + 'col-1-bucket2': expect.any(Object), + 'col-2-metric': expect.any(Object), + }); + }); + it('should not put date fields used outside date_histograms to the esaggs timeFields parameter', async () => { const queryBaseState: IndexPatternBaseState = { currentIndexPatternId: '1', diff --git a/x-pack/plugins/lens/public/indexpattern_datasource/to_expression.ts b/x-pack/plugins/lens/public/indexpattern_datasource/to_expression.ts index e2c4323b56c2a..ea7aa62054e5c 100644 --- a/x-pack/plugins/lens/public/indexpattern_datasource/to_expression.ts +++ b/x-pack/plugins/lens/public/indexpattern_datasource/to_expression.ts @@ -29,34 +29,16 @@ function getExpressionForLayer( } const columnEntries = columnOrder.map((colId) => [colId, columns[colId]] as const); - const bucketsCount = columnEntries.filter(([, entry]) => entry.isBucketed).length; - const metricsCount = columnEntries.length - bucketsCount; if (columnEntries.length) { const aggs = columnEntries.map(([colId, col]) => { return getEsAggsConfig(col, colId); }); - /** - * Because we are turning on metrics at all levels, the sequence generation - * logic here is more complicated. Examples follow: - * - * Example 1: [Count] - * Output: [`col-0-count`] - * - * Example 2: [Terms, Terms, Count] - * Output: [`col-0-terms0`, `col-2-terms1`, `col-3-count`] - * - * Example 3: [Terms, Terms, Count, Max] - * Output: [`col-0-terms0`, `col-3-terms1`, `col-4-count`, `col-5-max`] - */ const idMap = columnEntries.reduce((currentIdMap, [colId, column], index) => { - const newIndex = column.isBucketed - ? index * (metricsCount + 1) // Buckets are spaced apart by N + 1 - : (index ? index + 1 : 0) - bucketsCount + (bucketsCount - 1) * (metricsCount + 1); return { ...currentIdMap, - [`col-${columnEntries.length === 1 ? 0 : newIndex}-${colId}`]: { + [`col-${columnEntries.length === 1 ? 0 : index}-${colId}`]: { ...column, id: colId, }, @@ -122,8 +104,8 @@ function getExpressionForLayer( function: 'esaggs', arguments: { index: [indexPattern.id], - metricsAtAllLevels: [true], - partialRows: [true], + metricsAtAllLevels: [false], + partialRows: [false], includeFormatHints: [true], timeFields: allDateHistogramFields, aggConfigs: [JSON.stringify(aggs)], diff --git a/x-pack/plugins/lens/public/pie_visualization/render_function.tsx b/x-pack/plugins/lens/public/pie_visualization/render_function.tsx index cb2458a76967c..d4c85ce9b8843 100644 --- a/x-pack/plugins/lens/public/pie_visualization/render_function.tsx +++ b/x-pack/plugins/lens/public/pie_visualization/render_function.tsx @@ -27,8 +27,8 @@ import { import { FormatFactory, LensFilterEvent } from '../types'; import { VisualizationContainer } from '../visualization_container'; import { CHART_NAMES, DEFAULT_PERCENT_DECIMALS } from './constants'; -import { ColumnGroups, PieExpressionProps } from './types'; -import { getSliceValueWithFallback, getFilterContext } from './render_helpers'; +import { PieExpressionProps } from './types'; +import { getSliceValue, getFilterContext } from './render_helpers'; import { EmptyPlaceholder } from '../shared_components'; import './visualization.scss'; import { desanitizeFilterContext } from '../utils'; @@ -72,21 +72,6 @@ export function PieComponent( }); } - // The datatable for pie charts should include subtotals, like this: - // [bucket, subtotal, bucket, count] - // But the user only configured [bucket, bucket, count] - const columnGroups: ColumnGroups = []; - firstTable.columns.forEach((col) => { - if (groups.includes(col.id)) { - columnGroups.push({ - col, - metrics: [], - }); - } else if (columnGroups.length > 0) { - columnGroups[columnGroups.length - 1].metrics.push(col); - } - }); - const fillLabel: Partial = { textInvertible: false, valueFont: { @@ -100,7 +85,9 @@ export function PieComponent( fillLabel.valueFormatter = () => ''; } - const layers: PartitionLayer[] = columnGroups.map(({ col }, layerIndex) => { + const bucketColumns = firstTable.columns.filter((col) => groups.includes(col.id)); + + const layers: PartitionLayer[] = bucketColumns.map((col, layerIndex) => { return { groupByRollup: (d: Datum) => d[col.id] ?? EMPTY_SLICE, showAccessor: (d: Datum) => d !== EMPTY_SLICE, @@ -116,7 +103,7 @@ export function PieComponent( fillLabel: isDarkMode && shape === 'treemap' && - layerIndex < columnGroups.length - 1 && + layerIndex < bucketColumns.length - 1 && categoryDisplay !== 'hide' ? { ...fillLabel, textColor: euiDarkVars.euiTextColor } : fillLabel, @@ -136,10 +123,10 @@ export function PieComponent( if (shape === 'treemap') { // Only highlight the innermost color of the treemap, as it accurately represents area - return layerIndex < columnGroups.length - 1 ? 'rgba(0,0,0,0)' : outputColor; + return layerIndex < bucketColumns.length - 1 ? 'rgba(0,0,0,0)' : outputColor; } - const lighten = (d.depth - 1) / (columnGroups.length * 2); + const lighten = (d.depth - 1) / (bucketColumns.length * 2); return color(outputColor, 'hsl').lighten(lighten).hex(); }, }, @@ -198,8 +185,6 @@ export function PieComponent( setState({ isReady: true }); }, []); - const reverseGroups = [...columnGroups].reverse(); - const hasNegative = firstTable.rows.some((row) => { const value = row[metricColumn.id]; return typeof value === 'number' && value < 0; @@ -243,16 +228,12 @@ export function PieComponent( showLegend={ !hideLabels && (legendDisplay === 'show' || - (legendDisplay === 'default' && columnGroups.length > 1 && shape !== 'treemap')) + (legendDisplay === 'default' && bucketColumns.length > 1 && shape !== 'treemap')) } legendPosition={legendPosition || Position.Right} legendMaxDepth={nestedLegend ? undefined : 1 /* Color is based only on first layer */} onElementClick={(args) => { - const context = getFilterContext( - args[0][0] as LayerValue[], - columnGroups.map(({ col }) => col.id), - firstTable - ); + const context = getFilterContext(args[0][0] as LayerValue[], groups, firstTable); onClickValue(desanitizeFilterContext(context)); }} @@ -262,7 +243,7 @@ export function PieComponent( getSliceValueWithFallback(d, reverseGroups, metricColumn)} + valueAccessor={(d: Datum) => getSliceValue(d, metricColumn)} percentFormatter={(d: number) => percentFormatter.convert(d / 100)} valueGetter={hideLabels || numberDisplay === 'value' ? undefined : 'percent'} valueFormatter={(d: number) => (hideLabels ? '' : formatters[metricColumn.id].convert(d))} diff --git a/x-pack/plugins/lens/public/pie_visualization/render_helpers.test.ts b/x-pack/plugins/lens/public/pie_visualization/render_helpers.test.ts index d9ccda2a99ab2..22c63cd67281b 100644 --- a/x-pack/plugins/lens/public/pie_visualization/render_helpers.test.ts +++ b/x-pack/plugins/lens/public/pie_visualization/render_helpers.test.ts @@ -5,86 +5,47 @@ */ import { Datatable } from 'src/plugins/expressions/public'; -import { getSliceValueWithFallback, getFilterContext } from './render_helpers'; -import { ColumnGroups } from './types'; +import { getSliceValue, getFilterContext } from './render_helpers'; describe('render helpers', () => { - describe('#getSliceValueWithFallback', () => { - describe('without fallback', () => { - const columnGroups: ColumnGroups = [ - { col: { id: 'a', name: 'A', meta: { type: 'string' } }, metrics: [] }, - { col: { id: 'b', name: 'C', meta: { type: 'string' } }, metrics: [] }, - ]; - - it('returns the metric when positive number', () => { - expect( - getSliceValueWithFallback({ a: 'Cat', b: 'Home', c: 5 }, columnGroups, { + describe('#getSliceValue', () => { + it('returns the metric when positive number', () => { + expect( + getSliceValue( + { a: 'Cat', b: 'Home', c: 5 }, + { id: 'c', name: 'C', meta: { type: 'number' }, - }) - ).toEqual(5); - }); + } + ) + ).toEqual(5); + }); - it('returns the metric when negative number', () => { - expect( - getSliceValueWithFallback({ a: 'Cat', b: 'Home', c: -100 }, columnGroups, { + it('returns the metric when negative number', () => { + expect( + getSliceValue( + { a: 'Cat', b: 'Home', c: -100 }, + { id: 'c', name: 'C', meta: { type: 'number' }, - }) - ).toEqual(-100); - }); + } + ) + ).toEqual(-100); + }); - it('returns epsilon when metric is 0 without fallback', () => { - expect( - getSliceValueWithFallback({ a: 'Cat', b: 'Home', c: 0 }, columnGroups, { + it('returns epsilon when metric is 0 without fallback', () => { + expect( + getSliceValue( + { a: 'Cat', b: 'Home', c: 0 }, + { id: 'c', name: 'C', meta: { type: 'number' }, - }) - ).toEqual(Number.EPSILON); - }); - }); - - describe('fallback behavior', () => { - const columnGroups: ColumnGroups = [ - { - col: { id: 'a', name: 'A', meta: { type: 'string' } }, - metrics: [{ id: 'a_subtotal', name: '', meta: { type: 'number' } }], - }, - { col: { id: 'b', name: 'C', meta: { type: 'string' } }, metrics: [] }, - ]; - - it('falls back to metric from previous column if available', () => { - expect( - getSliceValueWithFallback( - { a: 'Cat', a_subtotal: 5, b: 'Home', c: undefined }, - columnGroups, - { id: 'c', name: 'C', meta: { type: 'number' } } - ) - ).toEqual(5); - }); - - it('uses epsilon if fallback is 0', () => { - expect( - getSliceValueWithFallback( - { a: 'Cat', a_subtotal: 0, b: 'Home', c: undefined }, - columnGroups, - { id: 'c', name: 'C', meta: { type: 'number' } } - ) - ).toEqual(Number.EPSILON); - }); - - it('uses epsilon if fallback is missing', () => { - expect( - getSliceValueWithFallback( - { a: 'Cat', a_subtotal: undefined, b: 'Home', c: undefined }, - columnGroups, - { id: 'c', name: 'C', meta: { type: 'number' } } - ) - ).toEqual(Number.EPSILON); - }); + } + ) + ).toEqual(Number.EPSILON); }); }); diff --git a/x-pack/plugins/lens/public/pie_visualization/render_helpers.ts b/x-pack/plugins/lens/public/pie_visualization/render_helpers.ts index 26b4f9ccda853..978afcca6a550 100644 --- a/x-pack/plugins/lens/public/pie_visualization/render_helpers.ts +++ b/x-pack/plugins/lens/public/pie_visualization/render_helpers.ts @@ -6,22 +6,13 @@ import { Datum, LayerValue } from '@elastic/charts'; import { Datatable, DatatableColumn } from 'src/plugins/expressions/public'; -import { ColumnGroups } from './types'; import { LensFilterEvent } from '../types'; -export function getSliceValueWithFallback( - d: Datum, - reverseGroups: ColumnGroups, - metricColumn: DatatableColumn -) { +export function getSliceValue(d: Datum, metricColumn: DatatableColumn) { if (typeof d[metricColumn.id] === 'number' && d[metricColumn.id] !== 0) { return d[metricColumn.id]; } - // Sometimes there is missing data for outer groups - // When there is missing data, we fall back to the next groups - // This creates a sunburst effect - const hasMetric = reverseGroups.find((group) => group.metrics.length && d[group.metrics[0].id]); - return hasMetric ? d[hasMetric.metrics[0].id] || Number.EPSILON : Number.EPSILON; + return Number.EPSILON; } export function getFilterContext( diff --git a/x-pack/plugins/lens/public/pie_visualization/types.ts b/x-pack/plugins/lens/public/pie_visualization/types.ts index 0596e54870a94..54bececa13c2a 100644 --- a/x-pack/plugins/lens/public/pie_visualization/types.ts +++ b/x-pack/plugins/lens/public/pie_visualization/types.ts @@ -4,7 +4,6 @@ * you may not use this file except in compliance with the Elastic License. */ -import { DatatableColumn } from 'src/plugins/expressions/public'; import { LensMultiTable } from '../types'; export interface SharedLayerState { @@ -38,8 +37,3 @@ export interface PieExpressionProps { data: LensMultiTable; args: PieExpressionArgs; } - -export type ColumnGroups = Array<{ - col: DatatableColumn; - metrics: DatatableColumn[]; -}>; diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.test.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.test.ts index 8076733be2d7d..0b708133d947b 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.test.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.test.ts @@ -411,7 +411,12 @@ describe('Detections Rules API', () => { describe('createPrepackagedRules', () => { beforeEach(() => { fetchMock.mockClear(); - fetchMock.mockResolvedValue('unknown'); + fetchMock.mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); }); test('check parameter url when creating pre-packaged rules', async () => { @@ -423,7 +428,12 @@ describe('Detections Rules API', () => { }); test('happy path', async () => { const resp = await createPrepackagedRules({ signal: abortCtrl.signal }); - expect(resp).toEqual(true); + expect(resp).toEqual({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); }); }); diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts index 23adfe0228333..ce1fdd18dbdef 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/api.ts @@ -245,13 +245,25 @@ export const duplicateRules = async ({ rules }: DuplicateRulesProps): Promise => { - await KibanaServices.get().http.fetch(DETECTION_ENGINE_PREPACKAGED_URL, { +export const createPrepackagedRules = async ({ + signal, +}: BasicFetchProps): Promise<{ + rules_installed: number; + rules_updated: number; + timelines_installed: number; + timelines_updated: number; +}> => { + const result = await KibanaServices.get().http.fetch<{ + rules_installed: number; + rules_updated: number; + timelines_installed: number; + timelines_updated: number; + }>(DETECTION_ENGINE_PREPACKAGED_URL, { method: 'PUT', signal, }); - return true; + return result; }; /** diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/translations.ts b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/translations.ts index 721790a36b27f..6e2aee9658658 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/translations.ts +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/translations.ts @@ -30,7 +30,21 @@ export const RULE_AND_TIMELINE_PREPACKAGED_FAILURE = i18n.translate( export const RULE_AND_TIMELINE_PREPACKAGED_SUCCESS = i18n.translate( 'xpack.securitySolution.containers.detectionEngine.createPrePackagedRuleAndTimelineSuccesDescription', { - defaultMessage: 'Installed pre-packaged rules and timelines from elastic', + defaultMessage: 'Installed pre-packaged rules and timeline templates from elastic', + } +); + +export const RULE_PREPACKAGED_SUCCESS = i18n.translate( + 'xpack.securitySolution.containers.detectionEngine.createPrePackagedRuleSuccesDescription', + { + defaultMessage: 'Installed pre-packaged rules from elastic', + } +); + +export const TIMELINE_PREPACKAGED_SUCCESS = i18n.translate( + 'xpack.securitySolution.containers.detectionEngine.createPrePackagedTimelineSuccesDescription', + { + defaultMessage: 'Installed pre-packaged timeline templates from elastic', } ); diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.test.tsx b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.test.tsx index 7f74e92584494..f6bd8c4359d6e 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.test.tsx +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.test.tsx @@ -3,12 +3,17 @@ * or more contributor license agreements. Licensed under the Elastic License; * you may not use this file except in compliance with the Elastic License. */ - +import { ReactElement } from 'react'; import { renderHook, act } from '@testing-library/react-hooks'; import { ReturnPrePackagedRulesAndTimelines, usePrePackagedRules } from './use_pre_packaged_rules'; import * as api from './api'; +import { shallow } from 'enzyme'; +import * as i18n from './translations'; -jest.mock('./api'); +jest.mock('./api', () => ({ + getPrePackagedRulesStatus: jest.fn(), + createPrepackagedRules: jest.fn(), +})); describe('usePrePackagedRules', () => { beforeEach(() => { @@ -52,6 +57,21 @@ describe('usePrePackagedRules', () => { }); test('fetch getPrePackagedRulesStatus', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 33, + rules_installed: 12, + rules_not_installed: 0, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 0, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); await act(async () => { const { result, waitForNextUpdate } = renderHook( () => @@ -87,7 +107,6 @@ describe('usePrePackagedRules', () => { }); test('happy path to createPrePackagedRules', async () => { - const spyOnCreatePrepackagedRules = jest.spyOn(api, 'createPrepackagedRules'); await act(async () => { const { result, waitForNextUpdate } = renderHook( () => @@ -106,7 +125,7 @@ describe('usePrePackagedRules', () => { resp = await result.current.createPrePackagedRules(); } expect(resp).toEqual(true); - expect(spyOnCreatePrepackagedRules).toHaveBeenCalled(); + expect(api.createPrepackagedRules).toHaveBeenCalled(); expect(result.current).toEqual({ getLoadPrebuiltRulesAndTemplatesButton: result.current.getLoadPrebuiltRulesAndTemplatesButton, @@ -127,6 +146,253 @@ describe('usePrePackagedRules', () => { }); }); + test('getLoadPrebuiltRulesAndTemplatesButton - LOAD_PREPACKAGED_RULES', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 0, + rules_not_installed: 1, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 0, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getLoadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + 'data-test-subj': 'button', + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="button"]').text()).toEqual(i18n.LOAD_PREPACKAGED_RULES); + }); + }); + + test('getLoadPrebuiltRulesAndTemplatesButton - LOAD_PREPACKAGED_TIMELINE_TEMPLATES', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 0, + rules_not_installed: 0, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 1, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getLoadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + 'data-test-subj': 'button', + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="button"]').text()).toEqual( + i18n.LOAD_PREPACKAGED_TIMELINE_TEMPLATES + ); + }); + }); + + test('getLoadPrebuiltRulesAndTemplatesButton - LOAD_PREPACKAGED_RULES_AND_TEMPLATES', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 0, + rules_not_installed: 1, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 1, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getLoadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + 'data-test-subj': 'button', + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="button"]').text()).toEqual( + i18n.LOAD_PREPACKAGED_RULES_AND_TEMPLATES + ); + }); + }); + + test('getReloadPrebuiltRulesAndTemplatesButton - missing rules and templates', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 1, + rules_not_installed: 1, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 1, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getReloadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="reloadPrebuiltRulesBtn"]').text()).toEqual( + 'Install 1 Elastic prebuilt rule and 1 Elastic prebuilt timeline ' + ); + }); + }); + + test('getReloadPrebuiltRulesAndTemplatesButton - missing rules', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 1, + rules_not_installed: 1, + rules_not_updated: 0, + timelines_installed: 0, + timelines_not_installed: 0, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getReloadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="reloadPrebuiltRulesBtn"]').text()).toEqual( + 'Install 1 Elastic prebuilt rule ' + ); + }); + }); + + test('getReloadPrebuiltRulesAndTemplatesButton - missing templates', async () => { + (api.getPrePackagedRulesStatus as jest.Mock).mockResolvedValue({ + rules_custom_installed: 0, + rules_installed: 1, + rules_not_installed: 0, + rules_not_updated: 0, + timelines_installed: 1, + timelines_not_installed: 1, + timelines_not_updated: 0, + }); + (api.createPrepackagedRules as jest.Mock).mockResolvedValue({ + rules_installed: 0, + rules_updated: 0, + timelines_installed: 0, + timelines_updated: 0, + }); + await act(async () => { + const { result, waitForNextUpdate } = renderHook( + () => + usePrePackagedRules({ + canUserCRUD: true, + hasIndexWrite: true, + isAuthenticated: true, + hasEncryptionKey: true, + isSignalIndexExists: true, + }) + ); + await waitForNextUpdate(); + await waitForNextUpdate(); + + const button = result.current.getReloadPrebuiltRulesAndTemplatesButton({ + isDisabled: false, + onClick: jest.fn(), + }); + const wrapper = shallow(button as ReactElement); + expect(wrapper.find('[data-test-subj="reloadPrebuiltRulesBtn"]').text()).toEqual( + 'Install 1 Elastic prebuilt timeline ' + ); + }); + }); + test('unhappy path to createPrePackagedRules', async () => { const spyOnCreatePrepackagedRules = jest.spyOn(api, 'createPrepackagedRules'); spyOnCreatePrepackagedRules.mockImplementation(() => { diff --git a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.tsx b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.tsx index 4d19f44bcfc84..48530ddeb181e 100644 --- a/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.tsx +++ b/x-pack/plugins/security_solution/public/detections/containers/detection_engine/rules/use_pre_packaged_rules.tsx @@ -114,6 +114,27 @@ export const usePrePackagedRules = ({ const [loadingCreatePrePackagedRules, setLoadingCreatePrePackagedRules] = useState(false); const [loading, setLoading] = useState(true); const [, dispatchToaster] = useStateToaster(); + const getSuccessToastMessage = (result: { + rules_installed: number; + rules_updated: number; + timelines_installed: number; + timelines_updated: number; + }) => { + const { + rules_installed: rulesInstalled, + rules_updated: rulesUpdated, + timelines_installed: timelinesInstalled, + timelines_updated: timelinesUpdated, + } = result; + if (rulesInstalled === 0 && (timelinesInstalled > 0 || timelinesUpdated > 0)) { + return i18n.TIMELINE_PREPACKAGED_SUCCESS; + } else if ((rulesInstalled > 0 || rulesUpdated > 0) && timelinesInstalled === 0) { + return i18n.RULE_PREPACKAGED_SUCCESS; + } else { + return i18n.RULE_AND_TIMELINE_PREPACKAGED_SUCCESS; + } + }; + useEffect(() => { let isSubscribed = true; const abortCtrl = new AbortController(); @@ -170,7 +191,7 @@ export const usePrePackagedRules = ({ isSignalIndexExists ) { setLoadingCreatePrePackagedRules(true); - await createPrepackagedRules({ + const result = await createPrepackagedRules({ signal: abortCtrl.signal, }); @@ -209,11 +230,7 @@ export const usePrePackagedRules = ({ timelinesNotInstalled: prePackagedRuleStatusResponse.timelines_not_installed, timelinesNotUpdated: prePackagedRuleStatusResponse.timelines_not_updated, }); - - displaySuccessToast( - i18n.RULE_AND_TIMELINE_PREPACKAGED_SUCCESS, - dispatchToaster - ); + displaySuccessToast(getSuccessToastMessage(result), dispatchToaster); stopTimeOut(); resolve(true); } else { @@ -277,8 +294,9 @@ export const usePrePackagedRules = ({ ); const getLoadPrebuiltRulesAndTemplatesButton = useCallback( ({ isDisabled, onClick, fill, 'data-test-subj': dataTestSubj = 'loadPrebuiltRulesBtn' }) => { - return prePackagedRuleStatus === 'ruleNotInstalled' || - prePackagedTimelineStatus === 'timelinesNotInstalled' ? ( + return (prePackagedRuleStatus === 'ruleNotInstalled' || + prePackagedTimelineStatus === 'timelinesNotInstalled') && + prePackagedRuleStatus !== 'someRuleUninstall' ? ( { } } /> + `); }); diff --git a/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_journey.tsx b/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_journey.tsx index 2ffb3f0feb4dd..9a3e045017f9a 100644 --- a/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_journey.tsx +++ b/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_journey.tsx @@ -79,6 +79,7 @@ export const ExecutedJourney: FC = ({ journey }) => ( {journey.steps.filter(isStepEnd).map((step, index) => ( ))} +
); diff --git a/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_step.tsx b/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_step.tsx index 3c26ba12eea65..5966851973af2 100644 --- a/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_step.tsx +++ b/x-pack/plugins/uptime/public/components/monitor/synthetics/executed_step.tsx @@ -41,7 +41,7 @@ export const ExecutedStep: FC = ({ step, index }) => (
- +
@@ -87,6 +87,5 @@ export const ExecutedStep: FC = ({ step, index }) => (
- ); diff --git a/x-pack/plugins/uptime/public/components/monitor/synthetics/step_screenshot_display.tsx b/x-pack/plugins/uptime/public/components/monitor/synthetics/step_screenshot_display.tsx index 2e8ad4bd0c9a8..b81cf6bc1ec1d 100644 --- a/x-pack/plugins/uptime/public/components/monitor/synthetics/step_screenshot_display.tsx +++ b/x-pack/plugins/uptime/public/components/monitor/synthetics/step_screenshot_display.tsx @@ -16,7 +16,7 @@ import { i18n } from '@kbn/i18n'; import { FormattedMessage } from '@kbn/i18n/react'; import React, { useContext, useEffect, useRef, useState, FC } from 'react'; import { useIntersection } from 'react-use'; -import { UptimeThemeContext } from '../../../contexts'; +import { UptimeSettingsContext, UptimeThemeContext } from '../../../contexts'; interface StepScreenshotDisplayProps { screenshotExists?: boolean; @@ -41,6 +41,8 @@ export const StepScreenshotDisplay: FC = ({ colors: { lightestShade: pageBackground }, } = useContext(UptimeThemeContext); + const { basePath } = useContext(UptimeSettingsContext); + const [isImagePopoverOpen, setIsImagePopoverOpen] = useState(false); const [isOverlayOpen, setIsOverlayOpen] = useState(false); @@ -59,7 +61,7 @@ export const StepScreenshotDisplay: FC = ({ }, [hasIntersected, isIntersecting, setHasIntersected]); let content: JSX.Element | null = null; - const imgSrc = `/api/uptime/journey/screenshot/${checkGroup}/${stepIndex}`; + const imgSrc = basePath + `/api/uptime/journey/screenshot/${checkGroup}/${stepIndex}`; if (hasIntersected && screenshotExists) { content = ( <> diff --git a/x-pack/plugins/uptime/server/lib/requests/search/refine_potential_matches.ts b/x-pack/plugins/uptime/server/lib/requests/search/refine_potential_matches.ts index 98db43c5b2623..a864bfa591424 100644 --- a/x-pack/plugins/uptime/server/lib/requests/search/refine_potential_matches.ts +++ b/x-pack/plugins/uptime/server/lib/requests/search/refine_potential_matches.ts @@ -38,6 +38,12 @@ export const fullyMatchingIds = (queryResult: any, statusFilter?: string): Monit for (const locBucket of monBucket.location.buckets) { const latest = locBucket.summaries.latest.hits.hits[0]; + // It is possible for no latest summary to exist in this bucket if only partial + // non-summary docs exist + if (!latest) { + continue; + } + const latestStillMatching = locBucket.latest_matching.top.hits.hits[0]; // If the most recent document still matches the most recent document matching the current filters // we can include this in the result diff --git a/x-pack/test/api_integration/apis/uptime/rest/monitor_states_generated.ts b/x-pack/test/api_integration/apis/uptime/rest/monitor_states_generated.ts index 3e06373042d59..69571099a2642 100644 --- a/x-pack/test/api_integration/apis/uptime/rest/monitor_states_generated.ts +++ b/x-pack/test/api_integration/apis/uptime/rest/monitor_states_generated.ts @@ -24,6 +24,30 @@ export default function ({ getService }: FtrProviderContext) { before('load heartbeat data', () => getService('esArchiver').load('uptime/blank')); after('unload heartbeat index', () => getService('esArchiver').unload('uptime/blank')); + // In this case we don't actually have any monitors to display + // but the query should still return successfully. This has + // caused bugs in the past because a bucket of monitor data + // was available and the query code assumed at least one + // event would be a summary for each monitor. + // See https://github.com/elastic/kibana/issues/81950 + describe('checks with no summaries', async () => { + const testMonitorId = 'scope-test-id'; + before(async () => { + const es = getService('legacyEs'); + dateRangeStart = new Date().toISOString(); + await makeChecksWithStatus(es, testMonitorId, 1, numIps, 1, {}, 'up', (d) => { + delete d.summary; + return d; + }); + }); + + it('should return no monitors and have no errors', async () => { + const url = getBaseUrl(dateRangeStart, new Date().toISOString()); + const apiResponse = await supertest.get(url); + expect(apiResponse.status).to.equal(200); + }); + }); + describe('query document scoping with mismatched check statuses', async () => { let checks: any[] = []; let nonSummaryIp: string | null = null; diff --git a/x-pack/test/functional/apps/dashboard/async_search/async_search.ts b/x-pack/test/functional/apps/dashboard/async_search/async_search.ts index 6932a88635a67..4d37ee1589169 100644 --- a/x-pack/test/functional/apps/dashboard/async_search/async_search.ts +++ b/x-pack/test/functional/apps/dashboard/async_search/async_search.ts @@ -12,6 +12,9 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { const testSubjects = getService('testSubjects'); const log = getService('log'); const PageObjects = getPageObjects(['common', 'header', 'dashboard', 'visChart']); + const dashboardPanelActions = getService('dashboardPanelActions'); + const inspector = getService('inspector'); + const queryBar = getService('queryBar'); describe('dashboard with async search', () => { before(async function () { @@ -24,7 +27,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { it('not delayed should load', async () => { await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.gotoDashboardEditMode('Not Delayed'); + await PageObjects.dashboard.loadSavedDashboard('Not Delayed'); await PageObjects.header.waitUntilLoadingHasFinished(); await testSubjects.missingOrFail('embeddableErrorLabel'); const data = await PageObjects.visChart.getBarChartData('Sum of bytes'); @@ -33,7 +36,7 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { it('delayed should load', async () => { await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.gotoDashboardEditMode('Delayed 5s'); + await PageObjects.dashboard.loadSavedDashboard('Delayed 5s'); await PageObjects.header.waitUntilLoadingHasFinished(); await testSubjects.missingOrFail('embeddableErrorLabel'); const data = await PageObjects.visChart.getBarChartData(''); @@ -42,10 +45,47 @@ export default function ({ getService, getPageObjects }: FtrProviderContext) { it('timed out should show error', async () => { await PageObjects.common.navigateToApp('dashboard'); - await PageObjects.dashboard.gotoDashboardEditMode('Delayed 15s'); + await PageObjects.dashboard.loadSavedDashboard('Delayed 15s'); await PageObjects.header.waitUntilLoadingHasFinished(); await testSubjects.existOrFail('embeddableErrorLabel'); await testSubjects.existOrFail('searchTimeoutError'); }); + + it('multiple searches are grouped and only single error popup is shown', async () => { + await PageObjects.common.navigateToApp('dashboard'); + await PageObjects.dashboard.loadSavedDashboard('Multiple delayed'); + await PageObjects.header.waitUntilLoadingHasFinished(); + await testSubjects.existOrFail('embeddableErrorLabel'); + // there should be two failed panels + expect((await testSubjects.findAll('embeddableErrorLabel')).length).to.be(2); + // but only single error toast because searches are grouped + expect((await testSubjects.findAll('searchTimeoutError')).length).to.be(1); + + // check that session ids are the same + const getSearchSessionIdByPanel = async (panelTitle: string) => { + await dashboardPanelActions.openInspectorByTitle(panelTitle); + await inspector.openInspectorRequestsView(); + const searchSessionId = await ( + await testSubjects.find('inspectorRequestSearchSessionId') + ).getAttribute('data-search-session-id'); + await inspector.close(); + return searchSessionId; + }; + + const panel1SessionId1 = await getSearchSessionIdByPanel('Sum of Bytes by Extension'); + const panel2SessionId1 = await getSearchSessionIdByPanel( + 'Sum of Bytes by Extension (Delayed 5s)' + ); + expect(panel1SessionId1).to.be(panel2SessionId1); + + await queryBar.clickQuerySubmitButton(); + + const panel1SessionId2 = await getSearchSessionIdByPanel('Sum of Bytes by Extension'); + const panel2SessionId2 = await getSearchSessionIdByPanel( + 'Sum of Bytes by Extension (Delayed 5s)' + ); + expect(panel1SessionId2).to.be(panel2SessionId2); + expect(panel1SessionId1).not.to.be(panel1SessionId2); + }); }); } diff --git a/x-pack/test/functional/es_archives/dashboard/async_search/data.json b/x-pack/test/functional/es_archives/dashboard/async_search/data.json index 2990097e88d00..486c73f711a6b 100644 --- a/x-pack/test/functional/es_archives/dashboard/async_search/data.json +++ b/x-pack/test/functional/es_archives/dashboard/async_search/data.json @@ -194,4 +194,52 @@ } } +{ + "type": "doc", + "value": { + "id": "dashboard:a41c6790-075d-11eb-be70-0bd5e8b57d03", + "index": ".kibana", + "source": { + "dashboard": { + "description": "", + "hits": 0, + "kibanaSavedObjectMeta": { + "searchSourceJSON": "{\"query\":{\"query\":\"\",\"language\":\"kuery\"},\"filter\":[]}" + }, + "optionsJSON": "{\"useMargins\":true,\"hidePanelTitles\":false}", + "panelsJSON": "[{\"version\":\"8.0.0\",\"gridData\":{\"x\":0,\"y\":0,\"w\":24,\"h\":15,\"i\":\"ec585931-ce8e-43fd-aa94-a1a9612d24ba\"},\"panelIndex\":\"ec585931-ce8e-43fd-aa94-a1a9612d24ba\",\"embeddableConfig\":{},\"panelRefName\":\"panel_0\"},{\"version\":\"8.0.0\",\"gridData\":{\"x\":24,\"y\":0,\"w\":24,\"h\":15,\"i\":\"c7b18010-462b-4e55-a974-fdec2ae64b06\"},\"panelIndex\":\"c7b18010-462b-4e55-a974-fdec2ae64b06\",\"embeddableConfig\":{},\"panelRefName\":\"panel_1\"},{\"version\":\"8.0.0\",\"gridData\":{\"x\":0,\"y\":15,\"w\":24,\"h\":15,\"i\":\"e67704f7-20b7-4ade-8dee-972a9d187107\"},\"panelIndex\":\"e67704f7-20b7-4ade-8dee-972a9d187107\",\"embeddableConfig\":{},\"panelRefName\":\"panel_2\"},{\"version\":\"8.0.0\",\"gridData\":{\"x\":24,\"y\":15,\"w\":24,\"h\":15,\"i\":\"f0b03592-10f1-41cd-9929-0cb4163bcd16\"},\"panelIndex\":\"f0b03592-10f1-41cd-9929-0cb4163bcd16\",\"embeddableConfig\":{},\"panelRefName\":\"panel_3\"}]", + "refreshInterval": { "pause": true, "value": 0 }, + "timeFrom": "2015-09-19T17:34:10.297Z", + "timeRestore": true, + "timeTo": "2015-09-23T00:09:17.180Z", + "title": "Multiple delayed", + "version": 1 + }, + "references": [ + { + "id": "14501a50-01e3-11eb-9b63-176d7b28a352", + "name": "panel_0", + "type": "visualization" + }, + { + "id": "50a67010-075d-11eb-be70-0bd5e8b57d02", + "name": "panel_1", + "type": "visualization" + }, + { + "id": "6c9f3830-01e3-11eb-9b63-176d7b28a352", + "name": "panel_2", + "type": "visualization" + }, + { + "id": "50a67010-075d-11eb-be70-0bd5e8b57d02", + "name": "panel_3", + "type": "visualization" + } + ], + "type": "dashboard", + "updated_at": "2020-03-19T11:59:53.701Z" + } + } +} diff --git a/x-pack/test/ingest_manager_api_integration/apis/epm/install_remove_multiple.ts b/x-pack/test/ingest_manager_api_integration/apis/epm/install_remove_multiple.ts new file mode 100644 index 0000000000000..82072f59a482b --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/epm/install_remove_multiple.ts @@ -0,0 +1,106 @@ +/* + * 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 expect from '@kbn/expect'; +import { FtrProviderContext } from '../../../api_integration/ftr_provider_context'; +import { skipIfNoDockerRegistry } from '../../helpers'; + +export default function (providerContext: FtrProviderContext) { + const { getService } = providerContext; + const kibanaServer = getService('kibanaServer'); + const supertest = getService('supertest'); + const dockerServers = getService('dockerServers'); + const server = dockerServers.get('registry'); + const pkgName = 'all_assets'; + const pkgVersion = '0.1.0'; + const pkgKey = `${pkgName}-${pkgVersion}`; + const experimentalPkgName = 'experimental'; + const experimentalPkgKey = `${experimentalPkgName}-${pkgVersion}`; + const experimental2PkgName = 'experimental2'; + const experimental2PkgKey = `${experimental2PkgName}-${pkgVersion}`; + + const uninstallPackage = async (pkg: string) => { + await supertest.delete(`/api/fleet/epm/packages/${pkg}`).set('kbn-xsrf', 'xxxx'); + }; + const installPackage = async (pkg: string) => { + await supertest + .post(`/api/fleet/epm/packages/${pkg}`) + .set('kbn-xsrf', 'xxxx') + .send({ force: true }); + }; + + const installPackages = async (pkgs: string[]) => { + const installingPackagesPromise = pkgs.map((pkg) => installPackage(pkg)); + return Promise.all(installingPackagesPromise); + }; + const uninstallPackages = async (pkgs: string[]) => { + const uninstallingPackagesPromise = pkgs.map((pkg) => uninstallPackage(pkg)); + return Promise.all(uninstallingPackagesPromise); + }; + const expectPkgFieldToExist = async ( + fields: any[], + fieldName: string, + exists: boolean = true + ) => { + const fieldExists = fields.find((field: { name: string }) => field.name === fieldName); + if (exists) { + expect(fieldExists).not.to.be(undefined); + } else { + expect(fieldExists).to.be(undefined); + } + }; + describe('installs and uninstalls multiple packages side effects', async () => { + skipIfNoDockerRegistry(providerContext); + before(async () => { + if (!server.enabled) return; + await installPackages([pkgKey, experimentalPkgKey, experimental2PkgKey]); + }); + after(async () => { + if (!server.enabled) return; + await uninstallPackages([pkgKey, experimentalPkgKey, experimental2PkgKey]); + }); + it('should create index patterns from all installed packages, experimental or beta', async () => { + const resIndexPatternLogs = await kibanaServer.savedObjects.get({ + type: 'index-pattern', + id: 'logs-*', + }); + + const fieldsLogs = JSON.parse(resIndexPatternLogs.attributes.fields); + + expectPkgFieldToExist(fieldsLogs, 'logs_test_name'); + expectPkgFieldToExist(fieldsLogs, 'logs_experimental_name'); + expectPkgFieldToExist(fieldsLogs, 'logs_experimental2_name'); + const resIndexPatternMetrics = await kibanaServer.savedObjects.get({ + type: 'index-pattern', + id: 'metrics-*', + }); + const fieldsMetrics = JSON.parse(resIndexPatternMetrics.attributes.fields); + expectPkgFieldToExist(fieldsMetrics, 'metrics_test_name'); + expectPkgFieldToExist(fieldsMetrics, 'metrics_experimental_name'); + expectPkgFieldToExist(fieldsMetrics, 'metrics_experimental2_name'); + }); + it('should correctly recreate index patterns when a package is uninstalled', async () => { + await uninstallPackage(experimental2PkgKey); + const resIndexPatternLogs = await kibanaServer.savedObjects.get({ + type: 'index-pattern', + id: 'logs-*', + }); + const fields = JSON.parse(resIndexPatternLogs.attributes.fields); + expectPkgFieldToExist(fields, 'logs_test_name'); + expectPkgFieldToExist(fields, 'logs_experimental_name'); + expectPkgFieldToExist(fields, 'logs_experimental2_name', false); + const resIndexPatternMetrics = await kibanaServer.savedObjects.get({ + type: 'index-pattern', + id: 'metrics-*', + }); + const fieldsMetrics = JSON.parse(resIndexPatternMetrics.attributes.fields); + + expectPkgFieldToExist(fieldsMetrics, 'metrics_test_name'); + expectPkgFieldToExist(fieldsMetrics, 'metrics_experimental_name'); + expectPkgFieldToExist(fieldsMetrics, 'metrics_experimental2_name', false); + }); + }); +} diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/ecs.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/ecs.yml new file mode 100644 index 0000000000000..4c18291b7c5ad --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/ecs.yml @@ -0,0 +1,3 @@ +- name: logs_experimental_name + title: logs_experimental_title + type: keyword \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/fields.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/fields.yml new file mode 100644 index 0000000000000..6e003ed0ad147 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/fields/fields.yml @@ -0,0 +1,16 @@ +- name: data_stream.type + type: constant_keyword + description: > + Data stream type. +- name: data_stream.dataset + type: constant_keyword + description: > + Data stream dataset. +- name: data_stream.namespace + type: constant_keyword + description: > + Data stream namespace. +- name: '@timestamp' + type: date + description: > + Event timestamp. diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/manifest.yml new file mode 100644 index 0000000000000..9ac3c68a0be9e --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_logs/manifest.yml @@ -0,0 +1,9 @@ +title: Test Dataset + +type: logs + +elasticsearch: + index_template.mappings: + dynamic: false + index_template.settings: + index.lifecycle.name: reference diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/ecs.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/ecs.yml new file mode 100644 index 0000000000000..3cd2db230f437 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/ecs.yml @@ -0,0 +1,3 @@ +- name: metrics_experimental_name + title: metrics_experimental_title + type: keyword \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/fields.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/fields.yml new file mode 100644 index 0000000000000..6e003ed0ad147 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/fields/fields.yml @@ -0,0 +1,16 @@ +- name: data_stream.type + type: constant_keyword + description: > + Data stream type. +- name: data_stream.dataset + type: constant_keyword + description: > + Data stream dataset. +- name: data_stream.namespace + type: constant_keyword + description: > + Data stream namespace. +- name: '@timestamp' + type: date + description: > + Event timestamp. diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/manifest.yml new file mode 100644 index 0000000000000..6bc20442bd432 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/data_stream/test_metrics/manifest.yml @@ -0,0 +1,3 @@ +title: Test Dataset + +type: metrics \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/docs/README.md b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/docs/README.md new file mode 100644 index 0000000000000..8e524c4c71b5f --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/docs/README.md @@ -0,0 +1,3 @@ +# Test package + +For testing side effects when installing and removing multiple packages diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/img/logo_overrides_64_color.svg b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/img/logo_overrides_64_color.svg new file mode 100644 index 0000000000000..b03007a76ffcc --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/img/logo_overrides_64_color.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/manifest.yml new file mode 100644 index 0000000000000..9c83569a69cbe --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental/0.1.0/manifest.yml @@ -0,0 +1,20 @@ +format_version: 1.0.0 +name: experimental +title: experimental integration +description: This is a test package for testing experimental packages +version: 0.1.0 +categories: [] +release: experimental +type: integration +license: basic + +requirement: + elasticsearch: + versions: '>7.7.0' + kibana: + versions: '>7.7.0' + +icons: + - src: '/img/logo_overrides_64_color.svg' + size: '16x16' + type: 'image/svg+xml' diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/ecs.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/ecs.yml new file mode 100644 index 0000000000000..dad07fa9637af --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/ecs.yml @@ -0,0 +1,3 @@ +- name: logs_experimental2_name + title: logs_experimental2_title + type: keyword \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/fields.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/fields.yml new file mode 100644 index 0000000000000..6e003ed0ad147 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/fields/fields.yml @@ -0,0 +1,16 @@ +- name: data_stream.type + type: constant_keyword + description: > + Data stream type. +- name: data_stream.dataset + type: constant_keyword + description: > + Data stream dataset. +- name: data_stream.namespace + type: constant_keyword + description: > + Data stream namespace. +- name: '@timestamp' + type: date + description: > + Event timestamp. diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/manifest.yml new file mode 100644 index 0000000000000..9ac3c68a0be9e --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_logs/manifest.yml @@ -0,0 +1,9 @@ +title: Test Dataset + +type: logs + +elasticsearch: + index_template.mappings: + dynamic: false + index_template.settings: + index.lifecycle.name: reference diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/ecs.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/ecs.yml new file mode 100644 index 0000000000000..0b6a2efaacd33 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/ecs.yml @@ -0,0 +1,3 @@ +- name: metrics_experimental2_name + title: metrics_experimental2_title + type: keyword \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/fields.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/fields.yml new file mode 100644 index 0000000000000..6e003ed0ad147 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/fields/fields.yml @@ -0,0 +1,16 @@ +- name: data_stream.type + type: constant_keyword + description: > + Data stream type. +- name: data_stream.dataset + type: constant_keyword + description: > + Data stream dataset. +- name: data_stream.namespace + type: constant_keyword + description: > + Data stream namespace. +- name: '@timestamp' + type: date + description: > + Event timestamp. diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/manifest.yml new file mode 100644 index 0000000000000..6bc20442bd432 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/data_stream/test_metrics/manifest.yml @@ -0,0 +1,3 @@ +title: Test Dataset + +type: metrics \ No newline at end of file diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/docs/README.md b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/docs/README.md new file mode 100644 index 0000000000000..8e524c4c71b5f --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/docs/README.md @@ -0,0 +1,3 @@ +# Test package + +For testing side effects when installing and removing multiple packages diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/img/logo_overrides_64_color.svg b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/img/logo_overrides_64_color.svg new file mode 100644 index 0000000000000..b03007a76ffcc --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/img/logo_overrides_64_color.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/manifest.yml b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/manifest.yml new file mode 100644 index 0000000000000..766835dbde037 --- /dev/null +++ b/x-pack/test/ingest_manager_api_integration/apis/fixtures/test_packages/experimental2/0.1.0/manifest.yml @@ -0,0 +1,20 @@ +format_version: 1.0.0 +name: experimental2 +title: experimental integration +description: This is a test package for testing experimental packages +version: 0.1.0 +categories: [] +release: experimental +type: integration +license: basic + +requirement: + elasticsearch: + versions: '>7.7.0' + kibana: + versions: '>7.7.0' + +icons: + - src: '/img/logo_overrides_64_color.svg' + size: '16x16' + type: 'image/svg+xml'