mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 09:19:04 -04:00
[8.x] [ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts (#192377) (#193118)
# Backport This will backport the following commits from `main` to `8.x`: - [[ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts (#192377)](https://github.com/elastic/kibana/pull/192377) <!--- Backport version: 9.4.3 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Robert Jaszczurek","email":"92210485+rbrtj@users.noreply.github.com"},"sourceCommit":{"committedDate":"2024-09-17T07:53:32Z","message":"[ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts (#192377)\n\n## Summary\r\n\r\nFix for [#129304](https://github.com/elastic/kibana/issues/129304)\r\n\r\nPreviously, for distribution type charts, we displayed calendar event\r\nmarkers only for anomalous data points. The changes improve the display\r\nof event markers for such chart types, including showing calendar event\r\nmarkers even when there is no underlying data point.\r\n\r\n| Scenario | Before | After |\r\n| :---: | :---: | :---: |\r\n| Rare chart |\r\n\r\n|\r\n| Population chart | \r\n|\r\n| Single metric chart (no difference) |\r\n\r\n|","sha":"d5b1fdf49af8eb23210e3b15a20fe1f9b660eea8","branchLabelMapping":{"^v9.0.0$":"main","^v8.16.0$":"8.x","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:enhancement",":ml","Feature:Anomaly Detection","v9.0.0","Team:ML","v8.16.0"],"title":"[ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts","number":192377,"url":"https://github.com/elastic/kibana/pull/192377","mergeCommit":{"message":"[ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts (#192377)\n\n## Summary\r\n\r\nFix for [#129304](https://github.com/elastic/kibana/issues/129304)\r\n\r\nPreviously, for distribution type charts, we displayed calendar event\r\nmarkers only for anomalous data points. The changes improve the display\r\nof event markers for such chart types, including showing calendar event\r\nmarkers even when there is no underlying data point.\r\n\r\n| Scenario | Before | After |\r\n| :---: | :---: | :---: |\r\n| Rare chart |\r\n\r\n|\r\n| Population chart | \r\n|\r\n| Single metric chart (no difference) |\r\n\r\n|","sha":"d5b1fdf49af8eb23210e3b15a20fe1f9b660eea8"}},"sourceBranch":"main","suggestedTargetBranches":["8.x"],"targetPullRequestStates":[{"branch":"main","label":"v9.0.0","branchLabelMappingKey":"^v9.0.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/192377","number":192377,"mergeCommit":{"message":"[ML] Anomaly Explorer: Display markers for scheduled events in distribution type anomaly charts (#192377)\n\n## Summary\r\n\r\nFix for [#129304](https://github.com/elastic/kibana/issues/129304)\r\n\r\nPreviously, for distribution type charts, we displayed calendar event\r\nmarkers only for anomalous data points. The changes improve the display\r\nof event markers for such chart types, including showing calendar event\r\nmarkers even when there is no underlying data point.\r\n\r\n| Scenario | Before | After |\r\n| :---: | :---: | :---: |\r\n| Rare chart |\r\n\r\n|\r\n| Population chart | \r\n|\r\n| Single metric chart (no difference) |\r\n\r\n|","sha":"d5b1fdf49af8eb23210e3b15a20fe1f9b660eea8"}},{"branch":"8.x","label":"v8.16.0","branchLabelMappingKey":"^v8.16.0$","isSourceBranch":false,"state":"NOT_CREATED"}]}] BACKPORT--> Co-authored-by: Robert Jaszczurek <92210485+rbrtj@users.noreply.github.com>
This commit is contained in:
parent
12fcb6110a
commit
6113e6c1e5
3 changed files with 43 additions and 7 deletions
|
@ -13,3 +13,5 @@ export const CHART_TYPE = {
|
|||
} as const;
|
||||
|
||||
export type ChartType = (typeof CHART_TYPE)[keyof typeof CHART_TYPE];
|
||||
|
||||
export const SCHEDULE_EVENT_MARKER_ENTITY = 'schedule_event_marker_entity';
|
||||
|
|
|
@ -40,6 +40,7 @@ import { CHART_TYPE } from '../explorer_constants';
|
|||
import { CHART_HEIGHT, TRANSPARENT_BACKGROUND } from './constants';
|
||||
import { filter } from 'rxjs';
|
||||
import { drawCursor } from './utils/draw_anomaly_explorer_charts_cursor';
|
||||
import { SCHEDULE_EVENT_MARKER_ENTITY } from '../../../../common/constants/charts';
|
||||
|
||||
const CONTENT_WRAPPER_HEIGHT = 215;
|
||||
const SCHEDULED_EVENT_MARKER_HEIGHT = 5;
|
||||
|
@ -158,12 +159,29 @@ export class ExplorerChartDistribution extends React.Component {
|
|||
.key((d) => d.entity)
|
||||
.entries(chartData)
|
||||
.sort((a, b) => {
|
||||
// To display calendar event markers we populate the chart with fake data points.
|
||||
// If a category has fake data points, it should be sorted to the end.
|
||||
const aHasFakeData = a.values.some((d) => d.entity === SCHEDULE_EVENT_MARKER_ENTITY);
|
||||
const bHasFakeData = b.values.some((d) => d.entity === SCHEDULE_EVENT_MARKER_ENTITY);
|
||||
|
||||
if (aHasFakeData && !bHasFakeData) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (bHasFakeData && !aHasFakeData) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return b.values.length - a.values.length;
|
||||
})
|
||||
.filter((d, i) => {
|
||||
// only filter for rare charts
|
||||
if (chartType === CHART_TYPE.EVENT_DISTRIBUTION) {
|
||||
return i < categoryLimit || d.key === highlight;
|
||||
return (
|
||||
i < categoryLimit ||
|
||||
d.key === highlight ||
|
||||
d.values.some((d) => d.entity === SCHEDULE_EVENT_MARKER_ENTITY)
|
||||
);
|
||||
}
|
||||
return true;
|
||||
})
|
||||
|
@ -373,7 +391,8 @@ export class ExplorerChartDistribution extends React.Component {
|
|||
.orient('left')
|
||||
.innerTickSize(0)
|
||||
.outerTickSize(0)
|
||||
.tickPadding(10);
|
||||
.tickPadding(10)
|
||||
.tickFormat((d) => (d === SCHEDULE_EVENT_MARKER_ENTITY ? null : d));
|
||||
|
||||
if (fieldFormat !== undefined) {
|
||||
yAxis.tickFormat((d) => fieldFormat.convert(d, 'text'));
|
||||
|
@ -518,7 +537,8 @@ export class ExplorerChartDistribution extends React.Component {
|
|||
const tooltipData = [{ label: formattedDate }];
|
||||
const seriesKey = config.detectorLabel;
|
||||
|
||||
if (marker.entity !== undefined) {
|
||||
// Hide entity for scheduled events with mocked value.
|
||||
if (marker.entity !== undefined && marker.entity !== SCHEDULE_EVENT_MARKER_ENTITY) {
|
||||
tooltipData.push({
|
||||
label: i18n.translate('xpack.ml.explorer.distributionChart.entityLabel', {
|
||||
defaultMessage: 'entity',
|
||||
|
@ -590,7 +610,11 @@ export class ExplorerChartDistribution extends React.Component {
|
|||
});
|
||||
}
|
||||
}
|
||||
} else if (chartType !== CHART_TYPE.EVENT_DISTRIBUTION) {
|
||||
} else if (
|
||||
chartType !== CHART_TYPE.EVENT_DISTRIBUTION &&
|
||||
// Hide value for scheduled events with mocked value.
|
||||
marker.entity !== SCHEDULE_EVENT_MARKER_ENTITY
|
||||
) {
|
||||
tooltipData.push({
|
||||
label: i18n.translate(
|
||||
'xpack.ml.explorer.distributionChart.valueWithoutAnomalyScoreLabel',
|
||||
|
|
|
@ -53,7 +53,7 @@ import { parseInterval } from '../../../common/util/parse_interval';
|
|||
import { getDatafeedAggregations } from '../../../common/util/datafeed_utils';
|
||||
import { findAggField } from '../../../common/util/validation_utils';
|
||||
import type { ChartType } from '../../../common/constants/charts';
|
||||
import { CHART_TYPE } from '../../../common/constants/charts';
|
||||
import { CHART_TYPE, SCHEDULE_EVENT_MARKER_ENTITY } from '../../../common/constants/charts';
|
||||
import { getChartType } from '../../../common/util/chart_utils';
|
||||
import type { MlJob } from '../..';
|
||||
|
||||
|
@ -1124,9 +1124,19 @@ export function anomalyChartsDataProvider(mlClient: MlClient, client: IScopedClu
|
|||
each(scheduledEvents, (events, time) => {
|
||||
const chartPoint = findChartPointForTime(chartDataForPointSearch, Number(time));
|
||||
if (chartPoint !== undefined) {
|
||||
// Note if the scheduled event coincides with an absence of the underlying metric data,
|
||||
// we don't worry about plotting the event.
|
||||
chartPoint.scheduledEvents = events;
|
||||
// We do not want to create additional points for single metric charts
|
||||
// as it could break the chart.
|
||||
} else if (chartType !== CHART_TYPE.SINGLE_METRIC) {
|
||||
// If there's no underlying metric data point for the scheduled event,
|
||||
// create a new chart point with a value of 0.
|
||||
const eventChartPoint: ChartPoint = {
|
||||
date: Number(time),
|
||||
value: 0,
|
||||
entity: SCHEDULE_EVENT_MARKER_ENTITY,
|
||||
scheduledEvents: events,
|
||||
};
|
||||
chartData.push(eventChartPoint);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue