diff --git a/x-pack/plugins/lens/public/xy_visualization/expression.test.tsx b/x-pack/plugins/lens/public/xy_visualization/expression.test.tsx index a4c1e1bd4ba1..a4b5d741c80f 100644 --- a/x-pack/plugins/lens/public/xy_visualization/expression.test.tsx +++ b/x-pack/plugins/lens/public/xy_visualization/expression.test.tsx @@ -18,7 +18,7 @@ import { Fit, } from '@elastic/charts'; import { PaletteOutput } from 'src/plugins/charts/public'; -import { xyChart, XYChart } from './expression'; +import { calculateMinInterval, xyChart, XYChart, XYChartProps } from './expression'; import { LensMultiTable } from '../types'; import { Datatable, DatatableRow } from '../../../../../src/plugins/expressions/public'; import React from 'react'; @@ -287,6 +287,10 @@ function sampleArgs() { { a: 1, b: 5, c: 'J', d: 'Bar' }, ]), }, + dateRange: { + fromDate: new Date('2019-01-02T05:00:00.000Z'), + toDate: new Date('2019-01-03T05:00:00.000Z'), + }, }; const args: XYArgs = createArgsWithLayers(); @@ -425,7 +429,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -449,7 +453,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -502,7 +506,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={undefined} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -516,7 +520,7 @@ describe('xy_expression', () => { `); }); - test('it generates correct xDomain for a layer with single value and a layer with no data (1-0) ', () => { + test('it uses passed in minInterval', () => { const data: LensMultiTable = { type: 'lens_multitable', tables: { @@ -539,7 +543,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -550,132 +554,10 @@ describe('xy_expression', () => { Object { "max": 1546491600000, "min": 1546405200000, - "minInterval": 1728000, + "minInterval": 50, } `); }); - - test('it generates correct xDomain for two layers with single value(1-1)', () => { - const data: LensMultiTable = { - type: 'lens_multitable', - tables: { - first: createSampleDatatableWithRows([{ a: 1, b: 2, c: 'I', d: 'Foo' }]), - second: createSampleDatatableWithRows([{ a: 10, b: 5, c: 'J', d: 'Bar' }]), - }, - }; - const component = shallow( - - ); - - expect(component.find(Settings).prop('xDomain')).toMatchInlineSnapshot(` - Object { - "max": 1546491600000, - "min": 1546405200000, - "minInterval": undefined, - } - `); - }); - test('it generates correct xDomain for a layer with single value and layer with multiple value data (1-n)', () => { - const data: LensMultiTable = { - type: 'lens_multitable', - tables: { - first: createSampleDatatableWithRows([{ a: 1, b: 2, c: 'I', d: 'Foo' }]), - second: createSampleDatatableWithRows([ - { a: 10, b: 5, c: 'J', d: 'Bar' }, - { a: 8, b: 5, c: 'K', d: 'Buzz' }, - ]), - }, - }; - const component = shallow( - - ); - - expect(component.find(Settings).prop('xDomain')).toMatchInlineSnapshot(` - Object { - "max": 1546491600000, - "min": 1546405200000, - "minInterval": undefined, - } - `); - }); - - test('it generates correct xDomain for 2 layers with multiple value data (n-n)', () => { - const data: LensMultiTable = { - type: 'lens_multitable', - tables: { - first: createSampleDatatableWithRows([ - { a: 1, b: 2, c: 'I', d: 'Foo' }, - { a: 8, b: 5, c: 'K', d: 'Buzz' }, - { a: 9, b: 7, c: 'L', d: 'Bar' }, - { a: 10, b: 2, c: 'G', d: 'Bear' }, - ]), - second: createSampleDatatableWithRows([ - { a: 10, b: 5, c: 'J', d: 'Bar' }, - { a: 8, b: 4, c: 'K', d: 'Fi' }, - { a: 1, b: 8, c: 'O', d: 'Pi' }, - ]), - }, - }; - const component = shallow( - - ); - - expect(component.find(Settings).prop('xDomain')).toMatchInlineSnapshot(` - Object { - "max": 1546491600000, - "min": 1546405200000, - "minInterval": undefined, - } - `); - }); }); test('it does not use date range if the x is not a time scale', () => { @@ -698,7 +580,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -716,7 +598,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -737,7 +619,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -758,7 +640,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -784,7 +666,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -808,7 +690,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -893,7 +775,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -945,7 +827,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -983,7 +865,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1004,7 +886,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1028,7 +910,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1061,7 +943,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1081,7 +963,7 @@ describe('xy_expression', () => { timeZone="CEST" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1107,7 +989,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1127,7 +1009,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1150,7 +1032,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1178,7 +1060,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1200,7 +1082,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1601,7 +1483,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1621,7 +1503,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1641,7 +1523,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1660,7 +1542,7 @@ describe('xy_expression', () => { formatFactory={getFormatSpy} chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} timeZone="UTC" onClickValue={onClickValue} onSelectRange={onSelectRange} @@ -1683,7 +1565,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1718,7 +1600,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1751,7 +1633,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1784,7 +1666,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1817,7 +1699,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1917,7 +1799,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -1991,7 +1873,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2063,7 +1945,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2087,7 +1969,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2110,7 +1992,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2133,7 +2015,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2168,7 +2050,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2195,7 +2077,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2217,7 +2099,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2244,7 +2126,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2277,7 +2159,7 @@ describe('xy_expression', () => { timeZone="UTC" chartsThemeService={chartsThemeService} paletteService={paletteService} - histogramBarTarget={50} + minInterval={50} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -2288,4 +2170,47 @@ describe('xy_expression', () => { }); }); }); + + describe('calculateMinInterval', () => { + let xyProps: XYChartProps; + + beforeEach(() => { + xyProps = sampleArgs(); + xyProps.args.layers[0].xScaleType = 'time'; + }); + it('should use first valid layer and determine interval', async () => { + const result = await calculateMinInterval( + xyProps, + jest.fn().mockResolvedValue({ interval: '5m' }) + ); + expect(result).toEqual(5 * 60 * 1000); + }); + + it('should return undefined if data table is empty', async () => { + xyProps.data.tables.first.rows = []; + const result = await calculateMinInterval( + xyProps, + jest.fn().mockResolvedValue({ interval: '5m' }) + ); + expect(result).toEqual(undefined); + }); + + it('should return undefined if interval can not be checked', async () => { + const result = await calculateMinInterval(xyProps, jest.fn().mockResolvedValue(undefined)); + expect(result).toEqual(undefined); + }); + + it('should return undefined if date column is not found', async () => { + xyProps.data.tables.first.columns.splice(2, 1); + const result = await calculateMinInterval(xyProps, jest.fn().mockResolvedValue(undefined)); + expect(result).toEqual(undefined); + }); + + it('should return undefined if x axis is not a date', async () => { + xyProps.args.layers[0].xScaleType = 'ordinal'; + xyProps.data.tables.first.columns.splice(2, 1); + const result = await calculateMinInterval(xyProps, jest.fn().mockResolvedValue(undefined)); + expect(result).toEqual(undefined); + }); + }); }); diff --git a/x-pack/plugins/lens/public/xy_visualization/expression.tsx b/x-pack/plugins/lens/public/xy_visualization/expression.tsx index 8713e3989a1b..54ae3bb759d2 100644 --- a/x-pack/plugins/lens/public/xy_visualization/expression.tsx +++ b/x-pack/plugins/lens/public/xy_visualization/expression.tsx @@ -8,7 +8,6 @@ import './expression.scss'; import React, { useState, useEffect } from 'react'; import ReactDOM from 'react-dom'; -import moment from 'moment'; import { Chart, Settings, @@ -39,10 +38,14 @@ import { LensFilterEvent, LensBrushEvent, } from '../types'; -import { XYArgs, SeriesType, visualizationTypes } from './types'; +import { XYArgs, SeriesType, visualizationTypes, LayerArgs } from './types'; import { VisualizationContainer } from '../visualization_container'; import { isHorizontalChart, getSeriesColor } from './state_helpers'; -import { ExpressionValueSearchContext, search } from '../../../../../src/plugins/data/public'; +import { + DataPublicPluginStart, + ExpressionValueSearchContext, + search, +} from '../../../../../src/plugins/data/public'; import { ChartsPluginSetup, PaletteRegistry, @@ -75,7 +78,7 @@ type XYChartRenderProps = XYChartProps & { paletteService: PaletteRegistry; formatFactory: FormatFactory; timeZone: string; - histogramBarTarget: number; + minInterval: number | undefined; onClickValue: (data: LensFilterEvent['data']) => void; onSelectRange: (data: LensBrushEvent['data']) => void; }; @@ -174,11 +177,31 @@ export const xyChart: ExpressionFunctionDefinition< }, }; +export async function calculateMinInterval( + { args: { layers }, data }: XYChartProps, + getIntervalByColumn: DataPublicPluginStart['search']['aggs']['getDateMetaByDatatableColumn'] +) { + const filteredLayers = getFilteredLayers(layers, data); + if (filteredLayers.length === 0) return; + const isTimeViz = data.dateRange && filteredLayers.every((l) => l.xScaleType === 'time'); + + if (!isTimeViz) return; + const dateColumn = data.tables[filteredLayers[0].layerId].columns.find( + (column) => column.id === filteredLayers[0].xAccessor + ); + if (!dateColumn) return; + const dateMetaData = await getIntervalByColumn(dateColumn); + if (!dateMetaData) return; + const intervalDuration = search.aggs.parseInterval(dateMetaData.interval); + if (!intervalDuration) return; + return intervalDuration.as('milliseconds'); +} + export const getXyChartRenderer = (dependencies: { formatFactory: Promise; chartsThemeService: ChartsPluginSetup['theme']; paletteService: PaletteRegistry; - histogramBarTarget: number; + getIntervalByColumn: DataPublicPluginStart['search']['aggs']['getDateMetaByDatatableColumn']; timeZone: string; }): ExpressionRenderDefinition => ({ name: 'lens_xy_chart_renderer', @@ -209,7 +232,7 @@ export const getXyChartRenderer = (dependencies: { chartsThemeService={dependencies.chartsThemeService} paletteService={dependencies.paletteService} timeZone={dependencies.timeZone} - histogramBarTarget={dependencies.histogramBarTarget} + minInterval={await calculateMinInterval(config, dependencies.getIntervalByColumn)} onClickValue={onClickValue} onSelectRange={onSelectRange} /> @@ -277,7 +300,7 @@ export function XYChart({ timeZone, chartsThemeService, paletteService, - histogramBarTarget, + minInterval, onClickValue, onSelectRange, }: XYChartRenderProps) { @@ -285,19 +308,7 @@ export function XYChart({ const chartTheme = chartsThemeService.useChartsTheme(); const chartBaseTheme = chartsThemeService.useChartsBaseTheme(); - const filteredLayers = layers.filter(({ layerId, xAccessor, accessors, splitAccessor }) => { - return !( - !accessors.length || - !data.tables[layerId] || - data.tables[layerId].rows.length === 0 || - (xAccessor && - data.tables[layerId].rows.every((row) => typeof row[xAccessor] === 'undefined')) || - // stacked percentage bars have no xAccessors but splitAccessor with undefined values in them when empty - (!xAccessor && - splitAccessor && - data.tables[layerId].rows.every((row) => typeof row[splitAccessor] === 'undefined')) - ); - }); + const filteredLayers = getFilteredLayers(layers, data); if (filteredLayers.length === 0) { const icon: IconType = layers.length > 0 ? getIconForSeriesType(layers[0].seriesType) : 'bar'; @@ -348,37 +359,6 @@ export function XYChart({ filteredBarLayers.some((layer) => layer.accessors.length > 1) || filteredBarLayers.some((layer) => layer.splitAccessor); - function calculateMinInterval() { - // check all the tables to see if all of the rows have the same timestamp - // that would mean that chart will draw a single bar - const isSingleTimestampInXDomain = () => { - const firstRowValue = - data.tables[filteredLayers[0].layerId].rows[0][filteredLayers[0].xAccessor!]; - for (const layer of filteredLayers) { - if ( - layer.xAccessor && - data.tables[layer.layerId].rows.some((row) => row[layer.xAccessor!] !== firstRowValue) - ) { - return false; - } - } - return true; - }; - - // add minInterval only for single point in domain - if (data.dateRange && isSingleTimestampInXDomain()) { - const params = xAxisColumn?.meta?.sourceParams?.params as Record; - if (params?.interval !== 'auto') - return search.aggs.parseInterval(params?.interval)?.asMilliseconds(); - - const { fromDate, toDate } = data.dateRange; - const duration = moment(toDate).diff(moment(fromDate)); - const targetMs = duration / histogramBarTarget; - return isNaN(targetMs) ? 0 : Math.max(Math.floor(targetMs), 1); - } - return undefined; - } - const isTimeViz = data.dateRange && filteredLayers.every((l) => l.xScaleType === 'time'); const isHistogramViz = filteredLayers.every((l) => l.isHistogram); @@ -386,7 +366,7 @@ export function XYChart({ ? { min: data.dateRange?.fromDate.getTime(), max: data.dateRange?.toDate.getTime(), - minInterval: calculateMinInterval(), + minInterval, } : undefined; @@ -802,6 +782,22 @@ export function XYChart({ ); } +function getFilteredLayers(layers: LayerArgs[], data: LensMultiTable) { + return layers.filter(({ layerId, xAccessor, accessors, splitAccessor }) => { + return !( + !accessors.length || + !data.tables[layerId] || + data.tables[layerId].rows.length === 0 || + (xAccessor && + data.tables[layerId].rows.every((row) => typeof row[xAccessor] === 'undefined')) || + // stacked percentage bars have no xAccessors but splitAccessor with undefined values in them when empty + (!xAccessor && + splitAccessor && + data.tables[layerId].rows.every((row) => typeof row[splitAccessor] === 'undefined')) + ); + }); +} + function assertNever(x: never): never { throw new Error('Unexpected series type: ' + x); } diff --git a/x-pack/plugins/lens/public/xy_visualization/index.ts b/x-pack/plugins/lens/public/xy_visualization/index.ts index 5e5eef2f01c1..ff719c222c5f 100644 --- a/x-pack/plugins/lens/public/xy_visualization/index.ts +++ b/x-pack/plugins/lens/public/xy_visualization/index.ts @@ -7,7 +7,6 @@ import { CoreSetup, IUiSettingsClient } from 'kibana/public'; import moment from 'moment-timezone'; import { ExpressionsSetup } from '../../../../../src/plugins/expressions/public'; -import { UI_SETTINGS } from '../../../../../src/plugins/data/public'; import { EditorFrameSetup, FormatFactory } from '../types'; import { ChartsPluginSetup } from '../../../../../src/plugins/charts/public'; import { LensPluginStartDependencies } from '../plugin'; @@ -63,7 +62,7 @@ export class XyVisualization { chartsThemeService: charts.theme, paletteService: palettes, timeZone: getTimeZone(core.uiSettings), - histogramBarTarget: core.uiSettings.get(UI_SETTINGS.HISTOGRAM_BAR_TARGET), + getIntervalByColumn: data.search.aggs.getDateMetaByDatatableColumn, }) ); return getXyVisualization({ paletteService: palettes, data });