Files
Konrad Lalik 2f0728ac67 Alerting: Matching instances preview for notification policies (#68882)
* Basic implementation in web worker

* Move instances discovery to the worker

* Remove filtering from the worker

* Use normalized routes, use rtk query for alert groups fetching

* Reorganize matchers utilities to be available for web workers

* Move object matchers to the machers util file, rename worker

* Move worker code to a separate hook, add perf logging

* Add a mock for the web worker code, fix tests

* Fix tests warnings

* Remove notification policy feature flag

* Add normalizeRoute tests, change the regex match to test for label matching

* Move worker init to the file scope

* Simplify useAsyncFn hook

* Use CorsWorker as a workaround for web workers loading from CDN

* Use a feature flag to enable/disable worker-based preview, add worker error handling

* Add POC for react-enable working with grafana feature toggles

* Code cleanup

* Remove console error, add useRouteGroupsMatcher tests

* Fix tests mock
2023-05-30 15:15:22 +02:00

111 lines
3.8 KiB
TypeScript

import {
AlertmanagerAlert,
AlertmanagerChoice,
AlertManagerCortexConfig,
AlertmanagerGroup,
ExternalAlertmanagerConfig,
ExternalAlertmanagers,
ExternalAlertmanagersResponse,
Matcher,
} from '../../../../plugins/datasource/alertmanager/types';
import { matcherToOperator } from '../utils/alertmanager';
import { getDatasourceAPIUid, GRAFANA_RULES_SOURCE_NAME } from '../utils/datasource';
import { alertingApi } from './alertingApi';
const LIMIT_TO_SUCCESSFULLY_APPLIED_AMS = 10;
export interface AlertmanagersChoiceResponse {
alertmanagersChoice: AlertmanagerChoice;
numExternalAlertmanagers: number;
}
interface AlertmanagerAlertsFilter {
active?: boolean;
silenced?: boolean;
inhibited?: boolean;
unprocessed?: boolean;
matchers?: Matcher[];
}
// Based on https://github.com/prometheus/alertmanager/blob/main/api/v2/openapi.yaml
export const alertmanagerApi = alertingApi.injectEndpoints({
endpoints: (build) => ({
getAlertmanagerAlerts: build.query<
AlertmanagerAlert[],
{ amSourceName: string; filter?: AlertmanagerAlertsFilter }
>({
query: ({ amSourceName, filter }) => {
// TODO Add support for active, silenced, inhibited, unprocessed filters
const filterMatchers = filter?.matchers
?.filter((matcher) => matcher.name && matcher.value)
.map((matcher) => `${matcher.name}${matcherToOperator(matcher)}${matcher.value}`);
const { silenced, inhibited, unprocessed, active } = filter || {};
const stateParams = Object.fromEntries(
Object.entries({ silenced, active, inhibited, unprocessed }).filter(([_, value]) => value !== undefined)
);
const params: Record<string, unknown> | undefined = { filter: filterMatchers };
if (stateParams) {
Object.keys(stateParams).forEach((key: string) => {
params[key] = stateParams[key];
});
}
return {
url: `/api/alertmanager/${getDatasourceAPIUid(amSourceName)}/api/v2/alerts`,
params,
};
},
}),
getAlertmanagerAlertGroups: build.query<AlertmanagerGroup[], { amSourceName: string }>({
query: ({ amSourceName }) => ({
url: `/api/alertmanager/${getDatasourceAPIUid(amSourceName)}/api/v2/alerts/groups`,
}),
}),
getAlertmanagerChoiceStatus: build.query<AlertmanagersChoiceResponse, void>({
query: () => ({ url: '/api/v1/ngalert' }),
providesTags: ['AlertmanagerChoice'],
}),
getExternalAlertmanagerConfig: build.query<ExternalAlertmanagerConfig, void>({
query: () => ({ url: '/api/v1/ngalert/admin_config' }),
providesTags: ['AlertmanagerChoice'],
}),
getExternalAlertmanagers: build.query<ExternalAlertmanagers, void>({
query: () => ({ url: '/api/v1/ngalert/alertmanagers' }),
transformResponse: (response: ExternalAlertmanagersResponse) => response.data,
}),
saveExternalAlertmanagersConfig: build.mutation<{ message: string }, ExternalAlertmanagerConfig>({
query: (config) => ({ url: '/api/v1/ngalert/admin_config', method: 'POST', data: config }),
invalidatesTags: ['AlertmanagerChoice'],
}),
getValidAlertManagersConfig: build.query<AlertManagerCortexConfig[], void>({
//this is only available for the "grafana" alert manager
query: () => ({
url: `/api/alertmanager/${getDatasourceAPIUid(
GRAFANA_RULES_SOURCE_NAME
)}/config/history?limit=${LIMIT_TO_SUCCESSFULLY_APPLIED_AMS}`,
}),
}),
resetAlertManagerConfigToOldVersion: build.mutation<{ message: string }, { id: number }>({
//this is only available for the "grafana" alert manager
query: (config) => ({
url: `/api/alertmanager/${getDatasourceAPIUid(GRAFANA_RULES_SOURCE_NAME)}/config/history/${
config.id
}/_activate`,
method: 'POST',
}),
}),
}),
});