"use strict"; var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault"); Object.defineProperty(exports, "__esModule", { value: true }); exports.supportedDataTypes = exports.showingBar = exports.metricLabel = exports.getMetricVisualization = exports.getDefaultColor = exports.DEFAULT_MAX_COLUMNS = void 0; var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends")); var _react = _interopRequireDefault(require("react")); var _i18n = require("@kbn/i18n"); var _public = require("@kbn/visualizations-plugin/public"); var _uiTheme = require("@kbn/ui-theme"); var _chartIcons = require("@kbn/chart-icons"); var _layer_types = require("../../../common/layer_types"); var _suggestions = require("./suggestions"); var _constants = require("./constants"); var _dimension_editor = require("./dimension_editor"); var _toolbar = require("./toolbar"); var _id_generator = require("../../id_generator"); var _to_expression = require("./to_expression"); var _utils = require("../../utils"); /* * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one * or more contributor license agreements. Licensed under the Elastic License * 2.0; you may not use this file except in compliance with the Elastic License * 2.0. */ const DEFAULT_MAX_COLUMNS = 3; exports.DEFAULT_MAX_COLUMNS = DEFAULT_MAX_COLUMNS; const showingBar = state => Boolean(state.showBar && state.maxAccessor); exports.showingBar = showingBar; const getDefaultColor = state => showingBar(state) ? _uiTheme.euiLightVars.euiColorPrimary : _uiTheme.euiThemeVars.euiColorLightestShade; exports.getDefaultColor = getDefaultColor; const supportedDataTypes = new Set(['number']); exports.supportedDataTypes = supportedDataTypes; const metricLabel = _i18n.i18n.translate('xpack.lens.metric.label', { defaultMessage: 'Metric' }); exports.metricLabel = metricLabel; const metricGroupLabel = _i18n.i18n.translate('xpack.lens.metric.groupLabel', { defaultMessage: 'Goal and single value' }); const getMetricLayerConfiguration = props => { const isSupportedMetric = op => !op.isBucketed && supportedDataTypes.has(op.dataType); const isSupportedDynamicMetric = op => !op.isBucketed && supportedDataTypes.has(op.dataType) && !op.isStaticValue; const getPrimaryAccessorDisplayConfig = () => { var _props$state$palette, _props$state$palette$; const stops = ((_props$state$palette = props.state.palette) === null || _props$state$palette === void 0 ? void 0 : (_props$state$palette$ = _props$state$palette.params) === null || _props$state$palette$ === void 0 ? void 0 : _props$state$palette$.stops) || []; const hasStaticColoring = !!props.state.color; const hasDynamicColoring = !!props.state.palette; return hasDynamicColoring ? { triggerIconType: 'colorBy', palette: stops.map(({ color }) => color) } : hasStaticColoring ? { triggerIconType: 'color', color: props.state.color } : { triggerIconType: 'color', color: getDefaultColor(props.state) }; }; const isBucketed = op => op.isBucketed; return { groups: [{ groupId: _constants.GROUP_ID.METRIC, dataTestSubj: 'lnsMetric_primaryMetricDimensionPanel', groupLabel: _i18n.i18n.translate('xpack.lens.primaryMetric.label', { defaultMessage: 'Primary metric' }), paramEditorCustomProps: { headingLabel: _i18n.i18n.translate('xpack.lens.primaryMetric.headingLabel', { defaultMessage: 'Value' }) }, accessors: props.state.metricAccessor ? [{ columnId: props.state.metricAccessor, ...getPrimaryAccessorDisplayConfig() }] : [], supportsMoreColumns: !props.state.metricAccessor, filterOperations: isSupportedDynamicMetric, isMetricDimension: true, enableDimensionEditor: true, enableFormatSelector: true, requiredMinDimensionCount: 1 }, { groupId: _constants.GROUP_ID.SECONDARY_METRIC, dataTestSubj: 'lnsMetric_secondaryMetricDimensionPanel', groupLabel: _i18n.i18n.translate('xpack.lens.metric.secondaryMetric', { defaultMessage: 'Secondary metric' }), paramEditorCustomProps: { headingLabel: _i18n.i18n.translate('xpack.lens.primaryMetric.headingLabel', { defaultMessage: 'Value' }) }, accessors: props.state.secondaryMetricAccessor ? [{ columnId: props.state.secondaryMetricAccessor }] : [], supportsMoreColumns: !props.state.secondaryMetricAccessor, filterOperations: isSupportedDynamicMetric, isMetricDimension: true, enableDimensionEditor: true, enableFormatSelector: true }, { groupId: _constants.GROUP_ID.MAX, dataTestSubj: 'lnsMetric_maxDimensionPanel', groupLabel: _i18n.i18n.translate('xpack.lens.metric.max', { defaultMessage: 'Maximum value' }), paramEditorCustomProps: { headingLabel: _i18n.i18n.translate('xpack.lens.primaryMetric.headingLabel', { defaultMessage: 'Value' }) }, accessors: props.state.maxAccessor ? [{ columnId: props.state.maxAccessor }] : [], supportsMoreColumns: !props.state.maxAccessor, filterOperations: isSupportedMetric, enableDimensionEditor: true, enableFormatSelector: false, supportStaticValue: true, prioritizedOperation: 'max', groupTooltip: _i18n.i18n.translate('xpack.lens.metric.maxTooltip', { defaultMessage: 'If the maximum value is specified, the minimum value is fixed at zero.' }) }, { groupId: _constants.GROUP_ID.BREAKDOWN_BY, dataTestSubj: 'lnsMetric_breakdownByDimensionPanel', groupLabel: _i18n.i18n.translate('xpack.lens.metric.breakdownBy', { defaultMessage: 'Break down by' }), accessors: props.state.breakdownByAccessor ? [{ columnId: props.state.breakdownByAccessor, triggerIconType: props.state.collapseFn ? 'aggregate' : undefined }] : [], supportsMoreColumns: !props.state.breakdownByAccessor, filterOperations: isBucketed, enableDimensionEditor: true, enableFormatSelector: true }] }; }; const getTrendlineLayerConfiguration = props => { return { hidden: true, groups: [{ groupId: _constants.GROUP_ID.TREND_METRIC, groupLabel: _i18n.i18n.translate('xpack.lens.primaryMetric.label', { defaultMessage: 'Primary metric' }), accessors: props.state.trendlineMetricAccessor ? [{ columnId: props.state.trendlineMetricAccessor }] : [], supportsMoreColumns: !props.state.trendlineMetricAccessor, filterOperations: () => false, hideGrouping: true, nestingOrder: 3 }, { groupId: _constants.GROUP_ID.TREND_SECONDARY_METRIC, groupLabel: _i18n.i18n.translate('xpack.lens.metric.secondaryMetric', { defaultMessage: 'Secondary metric' }), accessors: props.state.trendlineSecondaryMetricAccessor ? [{ columnId: props.state.trendlineSecondaryMetricAccessor }] : [], supportsMoreColumns: !props.state.trendlineSecondaryMetricAccessor, filterOperations: () => false, hideGrouping: true, nestingOrder: 2 }, { groupId: _constants.GROUP_ID.TREND_TIME, groupLabel: _i18n.i18n.translate('xpack.lens.metric.timeField', { defaultMessage: 'Time field' }), accessors: props.state.trendlineTimeAccessor ? [{ columnId: props.state.trendlineTimeAccessor }] : [], supportsMoreColumns: !props.state.trendlineTimeAccessor, filterOperations: () => false, hideGrouping: true, nestingOrder: 1 }, { groupId: _constants.GROUP_ID.TREND_BREAKDOWN_BY, groupLabel: _i18n.i18n.translate('xpack.lens.metric.breakdownBy', { defaultMessage: 'Break down by' }), accessors: props.state.trendlineBreakdownByAccessor ? [{ columnId: props.state.trendlineBreakdownByAccessor }] : [], supportsMoreColumns: !props.state.trendlineBreakdownByAccessor, filterOperations: () => false, hideGrouping: true, nestingOrder: 0 }] }; }; const removeMetricDimension = state => { delete state.metricAccessor; delete state.palette; delete state.color; }; const removeSecondaryMetricDimension = state => { delete state.secondaryMetricAccessor; delete state.secondaryPrefix; }; const removeMaxDimension = state => { delete state.maxAccessor; delete state.progressDirection; delete state.showBar; }; const removeBreakdownByDimension = state => { delete state.breakdownByAccessor; delete state.collapseFn; delete state.maxCols; }; const getMetricVisualization = ({ paletteService, theme }) => ({ id: _constants.LENS_METRIC_ID, visualizationTypes: [{ id: _constants.LENS_METRIC_ID, icon: _chartIcons.IconChartMetric, label: metricLabel, groupLabel: metricGroupLabel, showExperimentalBadge: true, sortPriority: 3 }], getVisualizationTypeId() { return _constants.LENS_METRIC_ID; }, clearLayer(state) { const newState = { ...state }; delete newState.subtitle; removeMetricDimension(newState); removeSecondaryMetricDimension(newState); removeMaxDimension(newState); removeBreakdownByDimension(newState); return newState; }, getLayerIds(state) { return state.trendlineLayerId ? [state.layerId, state.trendlineLayerId] : [state.layerId]; }, getDescription() { return { icon: _chartIcons.IconChartMetric, label: metricLabel }; }, getSuggestions: _suggestions.getSuggestions, initialize(addNewLayer, state, mainPalette) { return state !== null && state !== void 0 ? state : { layerId: addNewLayer(), layerType: _layer_types.layerTypes.DATA, palette: mainPalette }; }, triggers: [_public.VIS_EVENT_TO_TRIGGER.filter], getConfiguration(props) { return props.layerId === props.state.layerId ? getMetricLayerConfiguration(props) : getTrendlineLayerConfiguration(props); }, getLayerType(layerId, state) { if ((state === null || state === void 0 ? void 0 : state.layerId) === layerId) { return state.layerType; } if ((state === null || state === void 0 ? void 0 : state.trendlineLayerId) === layerId) { return state.trendlineLayerType; } }, getSupportedLayers(state) { return [{ type: _layer_types.layerTypes.DATA, label: _i18n.i18n.translate('xpack.lens.metric.addLayer', { defaultMessage: 'Visualization' }), initialDimensions: state ? [{ groupId: 'max', columnId: (0, _id_generator.generateId)(), staticValue: 0 }] : undefined, disabled: true }, { type: _layer_types.layerTypes.METRIC_TRENDLINE, label: _i18n.i18n.translate('xpack.lens.metric.layerType.trendLine', { defaultMessage: 'Trendline' }), initialDimensions: [{ groupId: _constants.GROUP_ID.TREND_TIME, columnId: (0, _id_generator.generateId)(), autoTimeField: true }], disabled: Boolean(state === null || state === void 0 ? void 0 : state.trendlineLayerId) }]; }, appendLayer(state, layerId, layerType) { if (layerType !== _layer_types.layerTypes.METRIC_TRENDLINE) { throw new Error(`Metric vis only supports layers of type ${_layer_types.layerTypes.METRIC_TRENDLINE}!`); } return { ...state, trendlineLayerId: layerId, trendlineLayerType: layerType }; }, removeLayer(state, layerId) { const newState = { ...state, ...(state.layerId === layerId && { metricAccessor: undefined }), trendlineLayerId: undefined, trendlineLayerType: undefined, trendlineMetricAccessor: undefined, trendlineTimeAccessor: undefined, trendlineBreakdownByAccessor: undefined }; return newState; }, getRemoveOperation(state, layerId) { return layerId === state.trendlineLayerId ? 'remove' : 'clear'; }, getLayersToLinkTo(state, newLayerId) { return newLayerId === state.trendlineLayerId ? [state.layerId] : []; }, getLinkedDimensions(state) { if (!state.trendlineLayerId) { return []; } const links = []; if (state.metricAccessor) { links.push({ from: { columnId: state.metricAccessor, groupId: _constants.GROUP_ID.METRIC, layerId: state.layerId }, to: { columnId: state.trendlineMetricAccessor, groupId: _constants.GROUP_ID.TREND_METRIC, layerId: state.trendlineLayerId } }); } if (state.secondaryMetricAccessor) { links.push({ from: { columnId: state.secondaryMetricAccessor, groupId: _constants.GROUP_ID.SECONDARY_METRIC, layerId: state.layerId }, to: { columnId: state.trendlineSecondaryMetricAccessor, groupId: _constants.GROUP_ID.TREND_SECONDARY_METRIC, layerId: state.trendlineLayerId } }); } if (state.breakdownByAccessor) { links.push({ from: { columnId: state.breakdownByAccessor, groupId: _constants.GROUP_ID.BREAKDOWN_BY, layerId: state.layerId }, to: { columnId: state.trendlineBreakdownByAccessor, groupId: _constants.GROUP_ID.TREND_BREAKDOWN_BY, layerId: state.trendlineLayerId } }); } return links; }, getLayersToRemoveOnIndexPatternChange: state => { return state.trendlineLayerId ? [state.trendlineLayerId] : []; }, toExpression: (state, datasourceLayers, attributes, datasourceExpressionsByLayers) => (0, _to_expression.toExpression)(paletteService, state, datasourceLayers, datasourceExpressionsByLayers), setDimension({ prevState, columnId, groupId }) { const updated = { ...prevState }; switch (groupId) { case _constants.GROUP_ID.METRIC: updated.metricAccessor = columnId; break; case _constants.GROUP_ID.SECONDARY_METRIC: updated.secondaryMetricAccessor = columnId; break; case _constants.GROUP_ID.MAX: updated.maxAccessor = columnId; if (!prevState.trendlineLayerId) { updated.showBar = true; } break; case _constants.GROUP_ID.BREAKDOWN_BY: updated.breakdownByAccessor = columnId; break; case _constants.GROUP_ID.TREND_TIME: updated.trendlineTimeAccessor = columnId; break; case _constants.GROUP_ID.TREND_METRIC: updated.trendlineMetricAccessor = columnId; break; case _constants.GROUP_ID.TREND_SECONDARY_METRIC: updated.trendlineSecondaryMetricAccessor = columnId; break; case _constants.GROUP_ID.TREND_BREAKDOWN_BY: updated.trendlineBreakdownByAccessor = columnId; break; } return updated; }, removeDimension({ prevState, columnId }) { const updated = { ...prevState }; if (prevState.metricAccessor === columnId) { removeMetricDimension(updated); } if (prevState.secondaryMetricAccessor === columnId) { removeSecondaryMetricDimension(updated); } if (prevState.maxAccessor === columnId) { removeMaxDimension(updated); } if (prevState.breakdownByAccessor === columnId) { removeBreakdownByDimension(updated); } if (prevState.trendlineTimeAccessor === columnId) { delete updated.trendlineTimeAccessor; } if (prevState.trendlineMetricAccessor === columnId) { delete updated.trendlineMetricAccessor; } if (prevState.trendlineSecondaryMetricAccessor === columnId) { delete updated.trendlineSecondaryMetricAccessor; } if (prevState.trendlineBreakdownByAccessor === columnId) { delete updated.trendlineBreakdownByAccessor; } return updated; }, ToolbarComponent(props) { return /*#__PURE__*/_react.default.createElement(_toolbar.Toolbar, props); }, DimensionEditorComponent(props) { return /*#__PURE__*/_react.default.createElement(_dimension_editor.DimensionEditor, (0, _extends2.default)({}, props, { paletteService: paletteService })); }, DimensionEditorAdditionalSectionComponent(props) { return /*#__PURE__*/_react.default.createElement(_dimension_editor.DimensionEditorAdditionalSection, props); }, getDisplayOptions() { return { noPanelTitle: false, noPadding: true }; }, getSuggestionFromConvertToLensContext({ suggestions, context }) { const allSuggestions = suggestions; const suggestion = { ...allSuggestions[0], datasourceState: { ...allSuggestions[0].datasourceState, layers: allSuggestions.reduce((acc, s) => { var _s$datasourceState; return { ...acc, ...((_s$datasourceState = s.datasourceState) === null || _s$datasourceState === void 0 ? void 0 : _s$datasourceState.layers) }; }, {}) }, visualizationState: { ...allSuggestions[0].visualizationState, ...context.configuration } }; return suggestion; }, getVisualizationInfo(state) { var _state$palette, _state$palette$params; const dimensions = []; if (state.metricAccessor) { dimensions.push({ id: state.metricAccessor, name: _i18n.i18n.translate('xpack.lens.primaryMetric.label', { defaultMessage: 'Primary metric' }), dimensionType: 'primary_metric' }); } if (state.secondaryMetricAccessor) { dimensions.push({ id: state.secondaryMetricAccessor, name: _i18n.i18n.translate('xpack.lens.metric.secondaryMetric', { defaultMessage: 'Secondary metric' }), dimensionType: 'secondary_metric' }); } if (state.maxAccessor) { dimensions.push({ id: state.maxAccessor, name: _i18n.i18n.translate('xpack.lens.metric.max', { defaultMessage: 'Maximum value' }), dimensionType: 'max' }); } if (state.breakdownByAccessor) { dimensions.push({ id: state.breakdownByAccessor, name: _i18n.i18n.translate('xpack.lens.metric.breakdownBy', { defaultMessage: 'Break down by' }), dimensionType: 'breakdown' }); } const stops = ((_state$palette = state.palette) === null || _state$palette === void 0 ? void 0 : (_state$palette$params = _state$palette.params) === null || _state$palette$params === void 0 ? void 0 : _state$palette$params.stops) || []; const hasStaticColoring = !!state.color; const hasDynamicColoring = !!state.palette; return { layers: [{ layerId: state.layerId, layerType: state.layerType, chartType: 'metric', ...this.getDescription(state), dimensions, palette: (hasDynamicColoring ? stops.map(({ color }) => color) : hasStaticColoring ? [state.color] : [getDefaultColor(state)]).filter(_utils.nonNullable) }] }; } }); exports.getMetricVisualization = getMetricVisualization;