mirror of
https://github.com/elastic/kibana.git
synced 2025-06-27 18:51:07 -04:00
[ResponseOps][Alerting] Hiding all features in a space causes rules to stop running (#146188)
Resolves https://github.com/elastic/kibana/issues/144638 ## Summary Removes logic that prevents rules from running when all features in a space are disabled. ### Checklist - [x] [Unit or functional tests](https://www.elastic.co/guide/en/kibana/master/development-tests.html) were updated or added to match the most common scenarios ### To verify - Create an alerting rule - Go to the [spaces page](http://localhost:5601/app/management/kibana/spaces), and disable all features in the space - Look at your terminal to see the alerting rule still running and no errors Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com>
This commit is contained in:
parent
b80a23ee12
commit
4f1552e338
8 changed files with 165 additions and 125 deletions
|
@ -45,6 +45,7 @@ const createRulesClientMock = () => {
|
|||
clearExpiredSnoozes: jest.fn(),
|
||||
runSoon: jest.fn(),
|
||||
clone: jest.fn(),
|
||||
getAlertFromRaw: jest.fn(),
|
||||
};
|
||||
return mocked;
|
||||
};
|
||||
|
|
|
@ -26,6 +26,16 @@ import {
|
|||
} from '../common';
|
||||
import { RulesClientContext } from '../types';
|
||||
|
||||
export interface GetAlertFromRawParams {
|
||||
id: string;
|
||||
ruleTypeId: string;
|
||||
rawRule: RawRule;
|
||||
references: SavedObjectReference[] | undefined;
|
||||
includeLegacyId?: boolean;
|
||||
excludeFromPublicApi?: boolean;
|
||||
includeSnoozeData?: boolean;
|
||||
}
|
||||
|
||||
export function getAlertFromRaw<Params extends RuleTypeParams>(
|
||||
context: RulesClientContext,
|
||||
id: string,
|
||||
|
|
|
@ -52,6 +52,7 @@ import { muteInstance } from './methods/mute_instance';
|
|||
import { unmuteInstance } from './methods/unmute_instance';
|
||||
import { runSoon } from './methods/run_soon';
|
||||
import { listAlertTypes } from './methods/list_alert_types';
|
||||
import { getAlertFromRaw, GetAlertFromRawParams } from './lib/get_alert_from_raw';
|
||||
|
||||
export type ConstructorOptions = Omit<
|
||||
RulesClientContext,
|
||||
|
@ -135,4 +136,16 @@ export class RulesClient {
|
|||
public getSpaceId(): string | undefined {
|
||||
return this.context.spaceId;
|
||||
}
|
||||
|
||||
public getAlertFromRaw = (params: GetAlertFromRawParams) =>
|
||||
getAlertFromRaw(
|
||||
this.context,
|
||||
params.id,
|
||||
params.ruleTypeId,
|
||||
params.rawRule,
|
||||
params.references,
|
||||
params.includeLegacyId,
|
||||
params.excludeFromPublicApi,
|
||||
params.includeSnoozeData
|
||||
);
|
||||
}
|
||||
|
|
|
@ -9,11 +9,11 @@ import { encryptedSavedObjectsMock } from '@kbn/encrypted-saved-objects-plugin/s
|
|||
import { CoreKibanaRequest } from '@kbn/core/server';
|
||||
import { schema } from '@kbn/config-schema';
|
||||
|
||||
import { getDecryptedAttributes, getFakeKibanaRequest, loadRule } from './rule_loader';
|
||||
import { getRuleAttributes, getFakeKibanaRequest, loadRule } from './rule_loader';
|
||||
import { TaskRunnerContext } from './task_runner_factory';
|
||||
import { ruleTypeRegistryMock } from '../rule_type_registry.mock';
|
||||
import { rulesClientMock } from '../rules_client.mock';
|
||||
import { Rule, RulesClientApi } from '../types';
|
||||
import { Rule } from '../types';
|
||||
import { MONITORING_HISTORY_LIMIT, RuleExecutionStatusErrorReasons } from '../../common';
|
||||
import { getReasonFromError } from '../lib/error_with_reason';
|
||||
import { alertingEventLoggerMock } from '../lib/alerting_event_logger/alerting_event_logger.mock';
|
||||
|
@ -137,25 +137,6 @@ describe('rule_loader', () => {
|
|||
expect(outcome).toBe('failure');
|
||||
});
|
||||
|
||||
test('throws when user cannot read rule', async () => {
|
||||
context.getRulesClientWithRequest = function (fakeRequest: unknown): RulesClientApi {
|
||||
rulesClient.get.mockImplementation(async (args: unknown) => {
|
||||
throw new Error('rule-client-error: 1001');
|
||||
});
|
||||
return rulesClient;
|
||||
};
|
||||
|
||||
let outcome = 'success';
|
||||
try {
|
||||
await loadRule({ ...DefaultLoadRuleParams, context });
|
||||
} catch (err) {
|
||||
outcome = 'failure';
|
||||
expect(err.message).toBe('rule-client-error: 1001');
|
||||
expect(getReasonFromError(err)).toBe(RuleExecutionStatusErrorReasons.Read);
|
||||
}
|
||||
expect(outcome).toBe('failure');
|
||||
});
|
||||
|
||||
test('throws when rule type is not enabled', async () => {
|
||||
ruleTypeRegistry.ensureRuleTypeEnabled.mockImplementation(() => {
|
||||
throw new Error('rule-type-not-enabled: 2112');
|
||||
|
@ -196,11 +177,14 @@ describe('rule_loader', () => {
|
|||
describe('getDecryptedAttributes()', () => {
|
||||
test('succeeds with default space', async () => {
|
||||
contextMock.spaceIdToNamespace.mockReturnValue(undefined);
|
||||
const result = await getDecryptedAttributes(context, ruleId, 'default');
|
||||
const result = await getRuleAttributes(context, ruleId, 'default');
|
||||
|
||||
expect(result.apiKey).toBe(apiKey);
|
||||
expect(result.consumer).toBe(consumer);
|
||||
expect(result.enabled).toBe(true);
|
||||
expect(result.fakeRequest).toEqual(expect.any(CoreKibanaRequest));
|
||||
expect(result.rule.alertTypeId).toBe(ruleTypeId);
|
||||
expect(result.rulesClient).toBeTruthy();
|
||||
expect(contextMock.spaceIdToNamespace.mock.calls[0]).toEqual(['default']);
|
||||
|
||||
const esoArgs = encryptedSavedObjects.getDecryptedAsInternalUser.mock.calls[0];
|
||||
|
@ -209,11 +193,14 @@ describe('rule_loader', () => {
|
|||
|
||||
test('succeeds with non-default space', async () => {
|
||||
contextMock.spaceIdToNamespace.mockReturnValue(spaceId);
|
||||
const result = await getDecryptedAttributes(context, ruleId, spaceId);
|
||||
const result = await getRuleAttributes(context, ruleId, spaceId);
|
||||
|
||||
expect(result.apiKey).toBe(apiKey);
|
||||
expect(result.consumer).toBe(consumer);
|
||||
expect(result.enabled).toBe(true);
|
||||
expect(result.fakeRequest).toEqual(expect.any(CoreKibanaRequest));
|
||||
expect(result.rule.alertTypeId).toBe(ruleTypeId);
|
||||
expect(result.rulesClient).toBeTruthy();
|
||||
expect(contextMock.spaceIdToNamespace.mock.calls[0]).toEqual([spaceId]);
|
||||
|
||||
const esoArgs = encryptedSavedObjects.getDecryptedAsInternalUser.mock.calls[0];
|
||||
|
@ -227,7 +214,7 @@ describe('rule_loader', () => {
|
|||
}
|
||||
);
|
||||
|
||||
const promise = getDecryptedAttributes(context, ruleId, spaceId);
|
||||
const promise = getRuleAttributes(context, ruleId, spaceId);
|
||||
await expect(promise).rejects.toThrow('wops');
|
||||
});
|
||||
});
|
||||
|
@ -340,20 +327,18 @@ function getTaskRunnerContext(ruleParameters: unknown, historyElements: number)
|
|||
getRulesClientWithRequest,
|
||||
};
|
||||
|
||||
function getRulesClientWithRequest(fakeRequest: unknown) {
|
||||
function getRulesClientWithRequest() {
|
||||
// only need get() mocked
|
||||
rulesClient.get.mockImplementation(async (args: unknown) => {
|
||||
return {
|
||||
name: ruleName,
|
||||
alertTypeId: ruleTypeId,
|
||||
params: ruleParameters,
|
||||
monitoring: {
|
||||
run: {
|
||||
history: new Array(historyElements),
|
||||
},
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
name: ruleName,
|
||||
alertTypeId: ruleTypeId,
|
||||
params: ruleParameters,
|
||||
monitoring: {
|
||||
run: {
|
||||
history: new Array(historyElements),
|
||||
},
|
||||
} as Rule;
|
||||
});
|
||||
},
|
||||
} as Rule);
|
||||
return rulesClient;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,6 +17,7 @@ import {
|
|||
RuleTypeRegistry,
|
||||
RuleTypeParamsValidator,
|
||||
SanitizedRule,
|
||||
RulesClientApi,
|
||||
} from '../types';
|
||||
import { MONITORING_HISTORY_LIMIT, RuleTypeParams } from '../../common';
|
||||
import { AlertingEventLogger } from '../lib/alerting_event_logger/alerting_event_logger';
|
||||
|
@ -35,11 +36,17 @@ export async function loadRule<Params extends RuleTypeParams>(params: LoadRulePa
|
|||
params;
|
||||
let enabled: boolean;
|
||||
let apiKey: string | null;
|
||||
let rule: SanitizedRule<Params>;
|
||||
let fakeRequest: CoreKibanaRequest;
|
||||
let rulesClient: RulesClientApi;
|
||||
|
||||
try {
|
||||
const decryptedAttributes = await getDecryptedAttributes(context, ruleId, spaceId);
|
||||
apiKey = decryptedAttributes.apiKey;
|
||||
enabled = decryptedAttributes.enabled;
|
||||
const attributes = await getRuleAttributes<Params>(context, ruleId, spaceId);
|
||||
apiKey = attributes.apiKey;
|
||||
enabled = attributes.enabled;
|
||||
rule = attributes.rule;
|
||||
fakeRequest = attributes.fakeRequest;
|
||||
rulesClient = attributes.rulesClient;
|
||||
} catch (err) {
|
||||
throw new ErrorWithReason(RuleExecutionStatusErrorReasons.Decrypt, err);
|
||||
}
|
||||
|
@ -51,18 +58,6 @@ export async function loadRule<Params extends RuleTypeParams>(params: LoadRulePa
|
|||
);
|
||||
}
|
||||
|
||||
const fakeRequest = getFakeKibanaRequest(context, spaceId, apiKey);
|
||||
const rulesClient = context.getRulesClientWithRequest(fakeRequest);
|
||||
|
||||
let rule: SanitizedRule<Params>;
|
||||
|
||||
// Ensure API key is still valid and user has access
|
||||
try {
|
||||
rule = await rulesClient.get<Params>({ id: ruleId });
|
||||
} catch (err) {
|
||||
throw new ErrorWithReason(RuleExecutionStatusErrorReasons.Read, err);
|
||||
}
|
||||
|
||||
alertingEventLogger.setRuleName(rule.name);
|
||||
|
||||
try {
|
||||
|
@ -94,24 +89,44 @@ export async function loadRule<Params extends RuleTypeParams>(params: LoadRulePa
|
|||
};
|
||||
}
|
||||
|
||||
export async function getDecryptedAttributes(
|
||||
export async function getRuleAttributes<Params extends RuleTypeParams>(
|
||||
context: TaskRunnerContext,
|
||||
ruleId: string,
|
||||
spaceId: string
|
||||
): Promise<{ apiKey: string | null; enabled: boolean; consumer: string }> {
|
||||
): Promise<{
|
||||
apiKey: string | null;
|
||||
enabled: boolean;
|
||||
consumer: string;
|
||||
rule: SanitizedRule<Params>;
|
||||
fakeRequest: CoreKibanaRequest;
|
||||
rulesClient: RulesClientApi;
|
||||
}> {
|
||||
const namespace = context.spaceIdToNamespace(spaceId);
|
||||
|
||||
// Only fetch encrypted attributes here, we'll create a saved objects client
|
||||
// scoped with the API key to fetch the remaining data.
|
||||
const {
|
||||
attributes: { apiKey, enabled, consumer },
|
||||
} = await context.encryptedSavedObjectsClient.getDecryptedAsInternalUser<RawRule>(
|
||||
const rawRule = await context.encryptedSavedObjectsClient.getDecryptedAsInternalUser<RawRule>(
|
||||
'alert',
|
||||
ruleId,
|
||||
{ namespace }
|
||||
);
|
||||
|
||||
return { apiKey, enabled, consumer };
|
||||
const fakeRequest = getFakeKibanaRequest(context, spaceId, rawRule.attributes.apiKey);
|
||||
const rulesClient = context.getRulesClientWithRequest(fakeRequest);
|
||||
const rule = rulesClient.getAlertFromRaw({
|
||||
id: ruleId,
|
||||
ruleTypeId: rawRule.attributes.alertTypeId as string,
|
||||
rawRule: rawRule.attributes as RawRule,
|
||||
references: rawRule.references,
|
||||
includeLegacyId: false,
|
||||
});
|
||||
|
||||
return {
|
||||
rule,
|
||||
apiKey: rawRule.attributes.apiKey,
|
||||
enabled: rawRule.attributes.enabled,
|
||||
consumer: rawRule.attributes.consumer,
|
||||
fakeRequest,
|
||||
rulesClient,
|
||||
};
|
||||
}
|
||||
|
||||
export function getFakeKibanaRequest(
|
||||
|
|
|
@ -14,6 +14,8 @@ import {
|
|||
AlertInstanceState,
|
||||
AlertInstanceContext,
|
||||
RuleExecutionStatusWarningReasons,
|
||||
Rule,
|
||||
RuleAction,
|
||||
} from '../types';
|
||||
import { ConcreteTaskInstance, isUnrecoverableError } from '@kbn/task-manager-plugin/server';
|
||||
import { TaskRunnerContext } from './task_runner_factory';
|
||||
|
@ -220,7 +222,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult).toEqual(generateRunnerResult({ state: true, history: [true] }));
|
||||
|
@ -320,7 +322,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
await taskRunner.run();
|
||||
expect(enqueueFunction).toHaveBeenCalledTimes(1);
|
||||
|
@ -402,8 +404,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
muteAll: true,
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
@ -527,8 +529,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
muteAll,
|
||||
snoozeSchedule: snoozeSchedule != null ? JSON.parse(snoozeSchedule) : [],
|
||||
});
|
||||
|
@ -580,8 +582,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
mutedInstanceIds: ['2'],
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
@ -663,8 +665,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onThrottleInterval',
|
||||
throttle: '1d',
|
||||
});
|
||||
|
@ -708,8 +710,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
mutedInstanceIds: ['2'],
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
});
|
||||
|
@ -765,8 +767,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
@ -833,8 +835,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalledTimes(1);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
@ -895,8 +897,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
await taskRunner.run();
|
||||
expect(
|
||||
customTaskRunnerFactoryInitializerParams.actionsPlugin.getActionsClientWithRequest
|
||||
|
@ -1009,7 +1011,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult.state.alertInstances).toEqual(
|
||||
|
@ -1138,7 +1140,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult.state.alertInstances).toEqual(
|
||||
|
@ -1243,8 +1245,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
actions: [
|
||||
{
|
||||
group: 'default',
|
||||
|
@ -1346,7 +1348,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult.state.alertInstances).toEqual(
|
||||
|
@ -1401,13 +1403,11 @@ describe('Task Runner', () => {
|
|||
inMemoryMetrics
|
||||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValueOnce(mockedRuleTypeSavedObject);
|
||||
rulesClient.get.mockResolvedValueOnce({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
schedule: { interval: '30s' },
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult).toEqual(
|
||||
|
@ -1439,7 +1439,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
|
||||
const runnerResult = await taskRunner.run();
|
||||
|
@ -1467,7 +1467,7 @@ describe('Task Runner', () => {
|
|||
|
||||
test('recovers gracefully when the Alert Task Runner throws an exception when loading rule to prepare for run', async () => {
|
||||
// used in loadRule() which is called in prepareToRun()
|
||||
rulesClient.get.mockImplementation(() => {
|
||||
rulesClient.getAlertFromRaw.mockImplementation(() => {
|
||||
throw new Error(GENERIC_ERROR_MESSAGE);
|
||||
});
|
||||
|
||||
|
@ -1488,7 +1488,7 @@ describe('Task Runner', () => {
|
|||
testAlertingEventLogCalls({
|
||||
setRuleName: false,
|
||||
status: 'error',
|
||||
errorReason: 'read',
|
||||
errorReason: 'decrypt',
|
||||
executionStatus: 'not-reached',
|
||||
});
|
||||
|
||||
|
@ -1550,7 +1550,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
const runnerResult = await taskRunner.run();
|
||||
|
@ -1624,7 +1624,7 @@ describe('Task Runner', () => {
|
|||
});
|
||||
|
||||
test('reschedules for smaller interval if es connectivity error encountered and schedule interval is greater than connectivity retry', async () => {
|
||||
rulesClient.get.mockImplementation(() => {
|
||||
rulesClient.getAlertFromRaw.mockImplementation(() => {
|
||||
throw SavedObjectsErrorHelpers.createGenericNotFoundEsUnavailableError('alert', '1');
|
||||
});
|
||||
|
||||
|
@ -1721,11 +1721,12 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
actions: [],
|
||||
});
|
||||
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
await taskRunner.run();
|
||||
|
||||
|
@ -1827,11 +1828,12 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
actions: [],
|
||||
});
|
||||
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
await taskRunner.run();
|
||||
|
||||
|
@ -1901,8 +1903,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
actions: [],
|
||||
});
|
||||
|
@ -1970,8 +1972,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
actions: [],
|
||||
});
|
||||
|
@ -2044,8 +2046,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
notifyWhen: 'onActionGroupChange',
|
||||
actions: [],
|
||||
});
|
||||
|
@ -2096,7 +2098,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult).toEqual(generateRunnerResult({ state: true, history: [true] }));
|
||||
|
@ -2161,8 +2163,8 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
const runnerResult = await taskRunner.run();
|
||||
expect(runnerResult).toEqual(generateRunnerResult({ state: true, history: [true] }));
|
||||
});
|
||||
|
@ -2176,7 +2178,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
ruleType.executor.mockImplementation(
|
||||
async ({
|
||||
|
@ -2204,7 +2206,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
await taskRunner.run();
|
||||
await taskRunner.run();
|
||||
|
@ -2238,11 +2240,11 @@ describe('Task Runner', () => {
|
|||
inMemoryMetrics
|
||||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
schedule: { interval: '50s' },
|
||||
});
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
await taskRunner.run();
|
||||
expect(
|
||||
|
@ -2263,7 +2265,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
ruleType.executor.mockImplementation(
|
||||
|
@ -2311,7 +2313,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
for (let i = 0; i < 300; i++) {
|
||||
|
@ -2378,12 +2380,13 @@ describe('Task Runner', () => {
|
|||
},
|
||||
];
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
actions: mockActions,
|
||||
} as jest.ResolvedValue<unknown>);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
actions: mockActions as RuleAction[],
|
||||
});
|
||||
|
||||
ruleTypeRegistry.get.mockReturnValue(ruleType);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue(SAVED_OBJECT);
|
||||
|
||||
const taskRunner = new TaskRunner(
|
||||
ruleType,
|
||||
|
@ -2514,8 +2517,8 @@ describe('Task Runner', () => {
|
|||
}
|
||||
);
|
||||
|
||||
rulesClient.get.mockResolvedValue({
|
||||
...mockedRuleTypeSavedObject,
|
||||
rulesClient.getAlertFromRaw.mockReturnValue({
|
||||
...(mockedRuleTypeSavedObject as Rule),
|
||||
actions: [
|
||||
{
|
||||
group: 'default',
|
||||
|
@ -2542,8 +2545,8 @@ describe('Task Runner', () => {
|
|||
id: '5',
|
||||
actionTypeId: 'any-action',
|
||||
},
|
||||
],
|
||||
} as jest.ResolvedValue<unknown>);
|
||||
] as RuleAction[],
|
||||
});
|
||||
|
||||
ruleTypeRegistry.get.mockReturnValue(ruleType);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce(SAVED_OBJECT);
|
||||
|
@ -2643,7 +2646,7 @@ describe('Task Runner', () => {
|
|||
);
|
||||
expect(AlertingEventLogger).toHaveBeenCalled();
|
||||
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue({
|
||||
id: '1',
|
||||
type: 'alert',
|
||||
|
|
|
@ -671,7 +671,18 @@ export class TaskRunner<
|
|||
|
||||
// fetch the rule again to ensure we return the correct schedule as it may have
|
||||
// changed during the task execution
|
||||
schedule = asOk((await preparedResult.rulesClient.get({ id: ruleId })).schedule);
|
||||
schedule = asOk(
|
||||
(
|
||||
await loadRule<Params>({
|
||||
paramValidator: this.ruleType.validate?.params,
|
||||
ruleId,
|
||||
spaceId,
|
||||
context: this.context,
|
||||
ruleTypeRegistry: this.ruleTypeRegistry,
|
||||
alertingEventLogger: this.alertingEventLogger,
|
||||
})
|
||||
).rule.schedule
|
||||
);
|
||||
} catch (err) {
|
||||
stateWithMetrics = asErr(err);
|
||||
schedule = asErr(err);
|
||||
|
|
|
@ -13,6 +13,7 @@ import {
|
|||
RuleTypeState,
|
||||
AlertInstanceState,
|
||||
AlertInstanceContext,
|
||||
Rule,
|
||||
} from '../types';
|
||||
import { ConcreteTaskInstance } from '@kbn/task-manager-plugin/server';
|
||||
import { TaskRunnerContext } from './task_runner_factory';
|
||||
|
@ -156,8 +157,9 @@ describe('Task Runner Cancel', () => {
|
|||
taskRunnerFactoryInitializerParams.executionContext.withContext.mockImplementation((ctx, fn) =>
|
||||
fn()
|
||||
);
|
||||
rulesClient.get.mockResolvedValue(mockedRuleTypeSavedObject);
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValueOnce({
|
||||
rulesClient.getAlertFromRaw.mockReturnValue(mockedRuleTypeSavedObject as Rule);
|
||||
|
||||
encryptedSavedObjectsClient.getDecryptedAsInternalUser.mockResolvedValue({
|
||||
id: '1',
|
||||
type: 'alert',
|
||||
attributes: {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue