diff --git a/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.getresolvedtimerange.md b/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.getresolvedtimerange.md
new file mode 100644
index 0000000000000..2af44037292a2
--- /dev/null
+++ b/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.getresolvedtimerange.md
@@ -0,0 +1,19 @@
+
+
+[Home](./index.md) > [kibana-plugin-plugins-data-public](./kibana-plugin-plugins-data-public.md) > [AggConfigs](./kibana-plugin-plugins-data-public.aggconfigs.md) > [getResolvedTimeRange](./kibana-plugin-plugins-data-public.aggconfigs.getresolvedtimerange.md)
+
+## AggConfigs.getResolvedTimeRange() method
+
+Returns the current time range as moment instance (date math will get resolved using the current "now" value or system time if not set)
+
+Signature:
+
+```typescript
+getResolvedTimeRange(): import("../..").TimeRangeBounds | undefined;
+```
+Returns:
+
+`import("../..").TimeRangeBounds | undefined`
+
+Current time range as resolved date.
+
diff --git a/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.md b/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.md
index 45333b6767cac..9e671675b0b29 100644
--- a/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.md
+++ b/docs/development/plugins/data/public/kibana-plugin-plugins-data-public.aggconfigs.md
@@ -42,6 +42,7 @@ export declare class AggConfigs
| [getAll()](./kibana-plugin-plugins-data-public.aggconfigs.getall.md) | | |
| [getRequestAggById(id)](./kibana-plugin-plugins-data-public.aggconfigs.getrequestaggbyid.md) | | |
| [getRequestAggs()](./kibana-plugin-plugins-data-public.aggconfigs.getrequestaggs.md) | | |
+| [getResolvedTimeRange()](./kibana-plugin-plugins-data-public.aggconfigs.getresolvedtimerange.md) | | Returns the current time range as moment instance (date math will get resolved using the current "now" value or system time if not set) |
| [getResponseAggById(id)](./kibana-plugin-plugins-data-public.aggconfigs.getresponseaggbyid.md) | | Find a response agg by it's id. This may be an agg in the aggConfigs, or one created specifically for a response value |
| [getResponseAggs()](./kibana-plugin-plugins-data-public.aggconfigs.getresponseaggs.md) | | Gets the AggConfigs (and possibly ResponseAggConfigs) that represent the values that will be produced when all aggs are run.With multi-value metric aggs it is possible for a single agg request to result in multiple agg values, which is why the length of a vis' responseValuesAggs may be different than the vis' aggs {array\[AggConfig\]} |
| [getSearchSourceTimeFilter(forceNow)](./kibana-plugin-plugins-data-public.aggconfigs.getsearchsourcetimefilter.md) | | |
diff --git a/src/plugins/data/common/search/aggs/agg_config.ts b/src/plugins/data/common/search/aggs/agg_config.ts
index 3c83b5bdf6084..9a35cf983c805 100644
--- a/src/plugins/data/common/search/aggs/agg_config.ts
+++ b/src/plugins/data/common/search/aggs/agg_config.ts
@@ -192,9 +192,8 @@ export class AggConfig {
} else if (!this.aggConfigs.timeRange) {
return;
}
- return moment.duration(
- moment(this.aggConfigs.timeRange.to).diff(this.aggConfigs.timeRange.from)
- );
+ const resolvedBounds = this.aggConfigs.getResolvedTimeRange()!;
+ return moment.duration(moment(resolvedBounds.max).diff(resolvedBounds.min));
}
return parsedTimeShift;
}
diff --git a/src/plugins/data/common/search/aggs/agg_configs.ts b/src/plugins/data/common/search/aggs/agg_configs.ts
index 8593a0b0ed0fa..c205b46e077f0 100644
--- a/src/plugins/data/common/search/aggs/agg_configs.ts
+++ b/src/plugins/data/common/search/aggs/agg_configs.ts
@@ -23,7 +23,7 @@ import { IAggType } from './agg_type';
import { AggTypesRegistryStart } from './agg_types_registry';
import { AggGroupNames } from './agg_groups';
import { IndexPattern } from '../../index_patterns/index_patterns/index_pattern';
-import { TimeRange, getTime, isRangeFilter } from '../../../common';
+import { TimeRange, getTime, isRangeFilter, calculateBounds } from '../../../common';
import { IBucketAggConfig } from './buckets';
import { insertTimeShiftSplit, mergeTimeShifts } from './utils/time_splits';
@@ -127,6 +127,19 @@ export class AggConfigs {
this.aggs.forEach(updateAggTimeRange);
}
+ /**
+ * Returns the current time range as moment instance (date math will get resolved using the current "now" value or system time if not set)
+ * @returns Current time range as resolved date.
+ */
+ getResolvedTimeRange() {
+ return (
+ this.timeRange &&
+ calculateBounds(this.timeRange, {
+ forceNow: this.forceNow,
+ })
+ );
+ }
+
// clone method will reuse existing AggConfig in the list (will not create new instances)
clone({ enabledOnly = true } = {}) {
const filterAggs = (agg: AggConfig) => {
diff --git a/src/plugins/data/public/public.api.md b/src/plugins/data/public/public.api.md
index d56727b468da6..4d9c69b137a3e 100644
--- a/src/plugins/data/public/public.api.md
+++ b/src/plugins/data/public/public.api.md
@@ -259,6 +259,7 @@ export class AggConfigs {
getRequestAggById(id: string): AggConfig | undefined;
// (undocumented)
getRequestAggs(): AggConfig[];
+ getResolvedTimeRange(): import("../..").TimeRangeBounds | undefined;
getResponseAggById(id: string): AggConfig | undefined;
getResponseAggs(): AggConfig[];
// (undocumented)
diff --git a/test/interpreter_functional/test_suites/run_pipeline/esaggs_timeshift.ts b/test/interpreter_functional/test_suites/run_pipeline/esaggs_timeshift.ts
index c750602f735bd..8fc09ce2d7342 100644
--- a/test/interpreter_functional/test_suites/run_pipeline/esaggs_timeshift.ts
+++ b/test/interpreter_functional/test_suites/run_pipeline/esaggs_timeshift.ts
@@ -71,6 +71,21 @@ export default function ({
expect(getCell(result, 0, 2)).to.be(4618);
});
+ it('shifts multiple metrics with relative time range and previous', async () => {
+ const expression = `
+ kibana_context timeRange={timerange from='${timeRange.from}' to='now'}
+ | esaggs index={indexPatternLoad id='logstash-*'}
+ aggs={aggCount id="1" enabled=true schema="metric"}
+ aggs={aggCount id="2" enabled=true schema="metric" timeShift="previous"}
+ `;
+ const result = await expectExpression(
+ 'esaggs_shift_multi_metric_previous',
+ expression
+ ).getResponse();
+ expect(getCell(result, 0, 0)).to.be(9247);
+ expect(getCell(result, 0, 1)).to.be(4763);
+ });
+
it('shifts single percentile', async () => {
const expression = `
kibana_context timeRange={timerange from='${timeRange.from}' to='${timeRange.to}'}
@@ -137,7 +152,7 @@ export default function ({
customMetric={aggAvg id="3"
field="bytes"
enabled=true
- schema="metric"
+ schema="metric"
}
enabled=true
schema="metric"
@@ -154,7 +169,7 @@ export default function ({
customMetric={aggAvg id="5"
field="bytes"
enabled=true
- schema="metric"
+ schema="metric"
}
enabled=true
schema="metric"