Skip to content

Commit

Permalink
Add KQL support to alert and actions find API (#47530)
Browse files Browse the repository at this point in the history
* Add KQL support to alert and actions find API

* Fix failing jest tests
  • Loading branch information
mikecote committed Oct 9, 2019
1 parent e927e5f commit 8ceac99
Show file tree
Hide file tree
Showing 8 changed files with 167 additions and 38 deletions.
1 change: 1 addition & 0 deletions x-pack/legacy/plugins/actions/server/actions_client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ interface FindOptions {
id: string;
};
fields?: string[];
filter?: string;
};
}

Expand Down
39 changes: 20 additions & 19 deletions x-pack/legacy/plugins/actions/server/routes/find.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,23 +41,24 @@ it('sends proper arguments to action find function', async () => {
expect(response).toEqual(expectedResult);
expect(actionsClient.find).toHaveBeenCalledTimes(1);
expect(actionsClient.find.mock.calls[0]).toMatchInlineSnapshot(`
Array [
Object {
"options": Object {
"defaultSearchOperator": "AND",
"fields": Array [
"description",
],
"hasReference": undefined,
"page": 1,
"perPage": 1,
"search": "text*",
"searchFields": Array [
"description",
],
"sortField": "description",
},
},
]
`);
Array [
Object {
"options": Object {
"defaultSearchOperator": "AND",
"fields": Array [
"description",
],
"filter": undefined,
"hasReference": undefined,
"page": 1,
"perPage": 1,
"search": "text*",
"searchFields": Array [
"description",
],
"sortField": "description",
},
},
]
`);
});
5 changes: 5 additions & 0 deletions x-pack/legacy/plugins/actions/server/routes/find.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ interface FindRequest extends WithoutQueryAndParams<Hapi.Request> {
id: string;
};
fields?: string[];
filter?: string;
};
}

Expand Down Expand Up @@ -58,6 +59,9 @@ export const findActionRoute = {
fields: Joi.array()
.items(Joi.string())
.single(),
filter: Joi.string()
.allow('')
.optional(),
})
.default(),
},
Expand All @@ -75,6 +79,7 @@ export const findActionRoute = {
sortField: query.sort_field,
hasReference: query.has_reference,
fields: query.fields,
filter: query.filter,
},
});
},
Expand Down
1 change: 1 addition & 0 deletions x-pack/legacy/plugins/alerting/server/alerts_client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ interface FindOptions {
id: string;
};
fields?: string[];
filter?: string;
};
}

Expand Down
39 changes: 20 additions & 19 deletions x-pack/legacy/plugins/alerting/server/routes/find.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,23 +40,24 @@ test('sends proper arguments to alert find function', async () => {
expect(response).toEqual(expectedResult);
expect(alertsClient.find).toHaveBeenCalledTimes(1);
expect(alertsClient.find.mock.calls[0]).toMatchInlineSnapshot(`
Array [
Object {
"options": Object {
"defaultSearchOperator": "AND",
"fields": Array [
"description",
],
"hasReference": undefined,
"page": 1,
"perPage": 1,
"search": "text*",
"searchFields": Array [
"description",
],
"sortField": "description",
},
},
]
`);
Array [
Object {
"options": Object {
"defaultSearchOperator": "AND",
"fields": Array [
"description",
],
"filter": undefined,
"hasReference": undefined,
"page": 1,
"perPage": 1,
"search": "text*",
"searchFields": Array [
"description",
],
"sortField": "description",
},
},
]
`);
});
5 changes: 5 additions & 0 deletions x-pack/legacy/plugins/alerting/server/routes/find.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ interface FindRequest extends WithoutQueryAndParams<Hapi.Request> {
id: string;
};
fields?: string[];
filter?: string;
};
}

Expand Down Expand Up @@ -58,6 +59,9 @@ export const findAlertRoute = {
fields: Joi.array()
.items(Joi.string())
.single(),
filter: Joi.string()
.allow('')
.optional(),
})
.default(),
},
Expand All @@ -75,6 +79,7 @@ export const findAlertRoute = {
sortField: query.sort_field,
hasReference: query.has_reference,
fields: query.fields,
filter: query.filter,
},
});
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,66 @@ export default function findActionTests({ getService }: FtrProviderContext) {
}
});

it('should handle find action request with filter appropriately', async () => {
const { body: createdAction } = await supertest
.post(`${getUrlPrefix(space.id)}/api/action`)
.set('kbn-xsrf', 'foo')
.send({
description: 'My action',
actionTypeId: 'test.index-record',
config: {
unencrypted: `This value shouldn't get encrypted`,
},
secrets: {
encrypted: 'This value should be encrypted',
},
})
.expect(200);
objectRemover.add(space.id, createdAction.id, 'action');

const response = await supertestWithoutAuth
.get(
`${getUrlPrefix(
space.id
)}/api/action/_find?filter=action.attributes.actionTypeId:test.index-record`
)
.auth(user.username, user.password);

switch (scenario.id) {
case 'no_kibana_privileges at space1':
case 'space_1_all at space2':
expect(response.statusCode).to.eql(404);
expect(response.body).to.eql({
statusCode: 404,
error: 'Not Found',
message: 'Not Found',
});
break;
case 'global_read at space1':
case 'superuser at space1':
case 'space_1_all at space1':
expect(response.statusCode).to.eql(200);
expect(response.body).to.eql({
page: 1,
perPage: 20,
total: 1,
data: [
{
id: createdAction.id,
description: 'My action',
actionTypeId: 'test.index-record',
config: {
unencrypted: `This value shouldn't get encrypted`,
},
},
],
});
break;
default:
throw new Error(`Scenario untested: ${JSON.stringify(scenario)}`);
}
});

it(`shouldn't find action from another space`, async () => {
const { body: createdAction } = await supertest
.post(`${getUrlPrefix(space.id)}/api/action`)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,61 @@ export default function createFindTests({ getService }: FtrProviderContext) {
}
});

it('should handle find alert request with filter appropriately', async () => {
const { body: createdAlert } = await supertest
.post(`${getUrlPrefix(space.id)}/api/alert`)
.set('kbn-xsrf', 'foo')
.send(getTestAlertData())
.expect(200);
objectRemover.add(space.id, createdAlert.id, 'alert');

const response = await supertestWithoutAuth
.get(
`${getUrlPrefix(
space.id
)}/api/alert/_find?filter=alert.attributes.alertTypeId:test.noop`
)
.auth(user.username, user.password);

switch (scenario.id) {
case 'no_kibana_privileges at space1':
case 'space_1_all at space2':
expect(response.statusCode).to.eql(404);
expect(response.body).to.eql({
statusCode: 404,
error: 'Not Found',
message: 'Not Found',
});
break;
case 'global_read at space1':
case 'superuser at space1':
case 'space_1_all at space1':
expect(response.statusCode).to.eql(200);
expect(response.body.page).to.equal(1);
expect(response.body.perPage).to.be.greaterThan(0);
expect(response.body.total).to.be.greaterThan(0);
const match = response.body.data.find((obj: any) => obj.id === createdAlert.id);
expect(match).to.eql({
id: createdAlert.id,
alertTypeId: 'test.noop',
interval: '10s',
enabled: true,
actions: [],
alertTypeParams: {},
createdBy: 'elastic',
scheduledTaskId: match.scheduledTaskId,
throttle: '1m',
updatedBy: 'elastic',
apiKeyOwner: 'elastic',
muteAll: false,
mutedInstanceIds: [],
});
break;
default:
throw new Error(`Scenario untested: ${JSON.stringify(scenario)}`);
}
});

it(`shouldn't find alert from another space`, async () => {
const { body: createdAlert } = await supertest
.post(`${getUrlPrefix(space.id)}/api/alert`)
Expand Down

0 comments on commit 8ceac99

Please sign in to comment.