Skip to content

Commit

Permalink
[Metrics UI] Add Jest tests for alert previews (elastic#74890)
Browse files Browse the repository at this point in the history
  • Loading branch information
Zacqary committed Aug 13, 2020
1 parent c2a1008 commit cede1ae
Show file tree
Hide file tree
Showing 3 changed files with 188 additions and 1 deletion.
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
/*
* 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 * as mocks from './test_mocks';
import { Comparator, Aggregators, MetricExpressionParams } from './types';
import { alertsMock, AlertServicesMock } from '../../../../../alerts/server/mocks';
import { previewMetricThresholdAlert } from './preview_metric_threshold_alert';

describe('Previewing the metric threshold alert type', () => {
describe('querying the entire infrastructure', () => {
test('returns the expected results using a bucket interval equal to the alert interval', async () => {
const [ungroupedResult] = await previewMetricThresholdAlert({
...baseParams,
lookback: 'h',
alertInterval: '1m',
});
const [firedResults, noDataResults, errorResults] = ungroupedResult;
expect(firedResults).toBe(30);
expect(noDataResults).toBe(0);
expect(errorResults).toBe(0);
});

test('returns the expected results using a bucket interval shorter than the alert interval', async () => {
const [ungroupedResult] = await previewMetricThresholdAlert({
...baseParams,
lookback: 'h',
alertInterval: '3m',
});
const [firedResults, noDataResults, errorResults] = ungroupedResult;
expect(firedResults).toBe(10);
expect(noDataResults).toBe(0);
expect(errorResults).toBe(0);
});
test('returns the expected results using a bucket interval longer than the alert interval', async () => {
const [ungroupedResult] = await previewMetricThresholdAlert({
...baseParams,
lookback: 'h',
alertInterval: '30s',
});
const [firedResults, noDataResults, errorResults] = ungroupedResult;
expect(firedResults).toBe(60);
expect(noDataResults).toBe(0);
expect(errorResults).toBe(0);
});
});
describe('querying with a groupBy parameter', () => {
test('returns the expected results', async () => {
const [resultA, resultB] = await previewMetricThresholdAlert({
...baseParams,
params: {
...baseParams.params,
groupBy: ['something'],
},
lookback: 'h',
alertInterval: '1m',
});
const [firedResultsA, noDataResultsA, errorResultsA] = resultA;
expect(firedResultsA).toBe(30);
expect(noDataResultsA).toBe(0);
expect(errorResultsA).toBe(0);
const [firedResultsB, noDataResultsB, errorResultsB] = resultB;
expect(firedResultsB).toBe(60);
expect(noDataResultsB).toBe(0);
expect(errorResultsB).toBe(0);
});
});
describe('querying a data set with a period of No Data', () => {
test('returns the expected results', async () => {
const [ungroupedResult] = await previewMetricThresholdAlert({
...baseParams,
params: {
...baseParams.params,
criteria: [
{
...baseCriterion,
metric: 'test.metric.2',
} as MetricExpressionParams,
],
},
lookback: 'h',
alertInterval: '1m',
});
const [firedResults, noDataResults, errorResults] = ungroupedResult;
expect(firedResults).toBe(25);
expect(noDataResults).toBe(10);
expect(errorResults).toBe(0);
});
});
});

const services: AlertServicesMock = alertsMock.createAlertServices();
services.callCluster.mockImplementation(async (_: string, { body, index }: any) => {
const metric = body.query.bool.filter[1]?.exists.field;
if (body.aggs.groupings) {
if (body.aggs.groupings.composite.after) {
return mocks.compositeEndResponse;
}
return mocks.basicCompositePreviewResponse;
}
if (metric === 'test.metric.2') {
return mocks.alternateMetricPreviewResponse;
}
return mocks.basicMetricPreviewResponse;
});

const baseCriterion = {
aggType: Aggregators.AVERAGE,
metric: 'test.metric.1',
timeSize: 1,
timeUnit: 'm',
comparator: Comparator.GT,
threshold: [0.75],
} as MetricExpressionParams;

const config = {
metricAlias: 'metricbeat-*',
fields: {
timefield: '@timestamp',
},
} as any;

const baseParams = {
callCluster: services.callCluster,
params: {
criteria: [baseCriterion],
groupBy: undefined,
filterQuery: undefined,
},
config,
};
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,13 @@ const bucketsC = [
},
];

const previewBucketsA = Array.from(Array(60), (_, i) => bucketsA[i % 2]); // Repeat bucketsA to a total length of 60
const previewBucketsB = Array.from(Array(60), (_, i) => bucketsB[i % 2]);
const previewBucketsWithNulls = [
...Array.from(Array(10), (_, i) => ({ aggregatedValue: { value: null } })),
...previewBucketsA.slice(10),
];

export const basicMetricResponse = {
aggregations: {
aggregatedIntervals: {
Expand Down Expand Up @@ -150,3 +157,50 @@ export const changedSourceIdResponse = {
},
},
};

export const basicMetricPreviewResponse = {
aggregations: {
aggregatedIntervals: {
buckets: previewBucketsA,
},
},
};

export const alternateMetricPreviewResponse = {
aggregations: {
aggregatedIntervals: {
buckets: previewBucketsWithNulls,
},
},
};

export const basicCompositePreviewResponse = {
aggregations: {
groupings: {
after_key: { groupBy0: 'foo' },
buckets: [
{
key: {
groupBy0: 'a',
},
aggregatedIntervals: {
buckets: previewBucketsA,
},
},
{
key: {
groupBy0: 'b',
},
aggregatedIntervals: {
buckets: previewBucketsB,
},
},
],
},
},
hits: {
total: {
value: 2,
},
},
};
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ interface NonCountMetricExpressionParams extends BaseMetricExpressionParams {
}

interface CountMetricExpressionParams extends BaseMetricExpressionParams {
aggType: 'count';
aggType: Aggregators.COUNT;
metric: never;
}

Expand Down

0 comments on commit cede1ae

Please sign in to comment.