Skip to content

Commit

Permalink
example es query with data api
Browse files Browse the repository at this point in the history
  • Loading branch information
gmmorris committed Apr 8, 2020
1 parent 267f22c commit af1e245
Show file tree
Hide file tree
Showing 11 changed files with 254 additions and 6 deletions.
44 changes: 44 additions & 0 deletions examples/alerting_example/public/alert_types/es_query.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
/*
* Licensed to Elasticsearch B.V. under one or more contributor
* license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright
* ownership. Elasticsearch B.V. licenses this file to you under
* the Apache License, Version 2.0 (the "License"); you may
* not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/

import React, { Fragment } from 'react';
import { AlertTypeModel } from '../../../../x-pack/plugins/triggers_actions_ui/public';

interface EsQueryParamsProps {
alertParams: {};
setAlertParams: (property: string, value: any) => void;
errors: { [key: string]: string[] };
}

export function getAlertType(): AlertTypeModel {
return {
id: 'example.es-query',
name: 'ES Query',
iconClass: 'bolt',
alertParamsExpression: () => <Fragment />,
validate: (alertParams: EsQueryParamsProps['alertParams']) => {
const validationResult = {
errors: {
instances: new Array<string>(),
},
};
return validationResult;
},
};
}
2 changes: 2 additions & 0 deletions examples/alerting_example/public/plugin.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import { TriggersAndActionsUIPublicPluginSetup } from '../../../x-pack/plugins/t
import { DataPublicPluginStart } from '../../../src/plugins/data/public';
import { getAlertType as getAlwaysFiringAlertType } from './alert_types/always_firing';
import { getAlertType as getPeopleInSpaceAlertType } from './alert_types/astros';
import { getAlertType as getESQueryAlertType } from './alert_types/es_query';
import { registerNavigation } from './alert_types';

export type Setup = void;
Expand Down Expand Up @@ -58,6 +59,7 @@ export class AlertingExamplePlugin implements Plugin<Setup, Start, AlertingExamp

triggers_actions_ui.alertTypeRegistry.register(getAlwaysFiringAlertType());
triggers_actions_ui.alertTypeRegistry.register(getPeopleInSpaceAlertType());
triggers_actions_ui.alertTypeRegistry.register(getESQueryAlertType());

registerNavigation(alerting);
}
Expand Down
172 changes: 172 additions & 0 deletions examples/alerting_example/server/alert_types/es_query.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,172 @@
/*
* Licensed to Elasticsearch B.V. under one or more contributor
* license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright
* ownership. Elasticsearch B.V. licenses this file to you under
* the Apache License, Version 2.0 (the "License"); you may
* not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/

import { AlertType } from '../../../../x-pack/plugins/alerting/server';
import { IEsSearchResponse } from '../../../../src/plugins/data/common';

export const alertType: AlertType = {
id: 'example.es-query',
name: 'ES Query',
actionGroups: [{ id: 'default', name: 'default' }],
defaultActionGroupId: 'default',
async executor({ services, params, state: { totalLastRun } }) {
const { strategy = EXAMPLE.serverStrategy, searchRequest = EXAMPLE } = params;

const res = (await services.search(searchRequest, {}, strategy)) as IEsSearchResponse;
const {
rawResponse: { hits: { total = 0, hits = [] } = {} },
} = res;

hits.map(hit => {
services
.alertInstanceFactory(hit._id)
.replaceState(hit)
.scheduleActions('default');
});

return {
totalLastRun: total,
};
},
};

const EXAMPLE = {
params: {
ignoreThrottled: true,
preference: 1586335820660,
index: 'kibana_sample_data_logs',
body: {
version: true,
size: 500,
sort: [
{
timestamp: {
order: 'desc',
unmapped_type: 'boolean',
},
},
],
aggs: {
'2': {
date_histogram: {
field: 'timestamp',
fixed_interval: '30s',
time_zone: 'Europe/London',
min_doc_count: 1,
},
},
},
stored_fields: ['*'],
script_fields: {
hour_of_day: {
script: {
source: "doc['timestamp'].value.getHour()",
lang: 'painless',
},
},
},
docvalue_fields: [
{
field: '@timestamp',
format: 'date_time',
},
{
field: 'timestamp',
format: 'date_time',
},
{
field: 'utc_time',
format: 'date_time',
},
],
_source: {
excludes: [],
},
query: {
bool: {
must: [],
filter: [
{
bool: {
should: [
{
bool: {
should: [
{
match_phrase: {
'geo.dest': 'CN',
},
},
],
minimum_should_match: 1,
},
},
{
bool: {
should: [
{
exists: {
field: 'host',
},
},
],
minimum_should_match: 1,
},
},
],
minimum_should_match: 1,
},
},
{
range: {
timestamp: {
gte: '2020-04-08T10:33:22.033Z',
lte: '2020-04-08T10:48:22.033Z',
format: 'strict_date_optional_time',
},
},
},
],
should: [],
must_not: [
{
match_phrase: {
agent: 'gidi',
},
},
],
},
},
highlight: {
pre_tags: ['@kibana-highlighted-field@'],
post_tags: ['@/kibana-highlighted-field@'],
fields: {
'*': {},
},
fragment_size: 2147483647,
},
},
rest_total_hits_as_int: true,
ignore_unavailable: true,
ignore_throttled: true,
timeout: '30000ms',
},
serverStrategy: 'es',
debug: true,
};
2 changes: 2 additions & 0 deletions examples/alerting_example/server/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import { Plugin, CoreSetup } from 'kibana/server';
import { PluginSetupContract as AlertingSetup } from '../../../x-pack/plugins/alerting/server';

import { alertType as esQueryAlert } from './alert_types/es_query';
import { alertType as alwaysFiringAlert } from './alert_types/always_firing';
import { alertType as peopleInSpaceAlert } from './alert_types/astros';

Expand All @@ -32,6 +33,7 @@ export class AlertingExamplePlugin implements Plugin<void, void, AlertingExample
public setup(core: CoreSetup, { alerting }: AlertingExampleDeps) {
alerting.registerType(alwaysFiringAlert);
alerting.registerType(peopleInSpaceAlert);
alerting.registerType(esQueryAlert);
}

public start() {}
Expand Down
1 change: 1 addition & 0 deletions src/plugins/data/server/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -166,6 +166,7 @@ export { ParsedInterval } from '../common';

export {
ISearch,
ISearchGeneric,
ISearchCancel,
ISearchOptions,
IRequestTypesMap,
Expand Down
5 changes: 4 additions & 1 deletion src/plugins/data/server/search/i_search_setup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,10 @@
* under the License.
*/

import { IContextProvider } from 'kibana/server';
import { IContextProvider, APICaller } from 'kibana/server';
import { ISearchContext } from './i_search_context';
import { TRegisterSearchStrategyProvider, TSearchStrategyProvider } from './i_search_strategy';
import { IRouteHandlerSearchContext } from './i_route_handler_search_context';

/**
* The setup contract exposed by the Search plugin exposes the search strategy extension
Expand All @@ -37,4 +38,6 @@ export interface ISearchSetup {
* strategies.
*/
registerSearchStrategyProvider: TRegisterSearchStrategyProvider;

createScopedSearchApi: (caller: APICaller) => IRouteHandlerSearchContext;
}
1 change: 1 addition & 0 deletions src/plugins/data/server/search/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ export { ISearchContext } from './i_search_context';

export {
ISearch,
ISearchGeneric,
ISearchCancel,
ISearchOptions,
IRequestTypesMap,
Expand Down
6 changes: 6 additions & 0 deletions src/plugins/data/server/search/search_service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,12 @@ export class SearchService implements Plugin<ISearchSetup, void> {
const api: ISearchSetup = {
registerSearchStrategyContext: this.contextContainer!.registerContext,
registerSearchStrategyProvider,
createScopedSearchApi: caller => {
return createApi({
caller,
searchStrategies: this.searchStrategies,
});
},
};

api.registerSearchStrategyContext(this.initializerContext.opaqueId, 'core', () => core);
Expand Down
9 changes: 8 additions & 1 deletion x-pack/plugins/alerting/kibana.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,13 @@
"version": "8.0.0",
"kibanaVersion": "kibana",
"configPath": ["xpack", "alerting"],
"requiredPlugins": ["licensing", "taskManager", "encryptedSavedObjects", "actions", "eventLog"],
"requiredPlugins": [
"licensing",
"taskManager",
"encryptedSavedObjects",
"actions",
"eventLog",
"data"
],
"optionalPlugins": ["usageCollection", "spaces", "security"]
}
16 changes: 12 additions & 4 deletions x-pack/plugins/alerting/server/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ import { Services } from './types';
import { registerAlertsUsageCollector } from './usage';
import { initializeAlertingTelemetry, scheduleAlertingTelemetry } from './usage/task';
import { IEventLogger, IEventLogService } from '../../event_log/server';
import { PluginSetup as DataPluginSetup } from '../../../../src/plugins/data/server';

const EVENT_LOG_PROVIDER = 'alerting';
export const EVENT_LOG_ACTIONS = {
Expand All @@ -83,6 +84,7 @@ export interface AlertingPluginsSetup {
spaces?: SpacesPluginSetup;
usageCollection?: UsageCollectionSetup;
eventLog: IEventLogService;
data: DataPluginSetup;
}
export interface AlertingPluginsStart {
actions: ActionsPluginStartContract;
Expand All @@ -104,6 +106,7 @@ export class AlertingPlugin {
private readonly telemetryLogger: Logger;
private readonly kibanaIndex: Promise<string>;
private eventLogger?: IEventLogger;
private data?: DataPluginSetup;

constructor(initializerContext: PluginInitializerContext) {
this.logger = initializerContext.logger.get('plugins', 'alerting');
Expand All @@ -123,6 +126,7 @@ export class AlertingPlugin {
this.licenseState = new LicenseState(plugins.licensing.license$);
this.spaces = plugins.spaces?.spacesService;
this.security = plugins.security;
this.data = plugins.data;
this.isESOUsingEphemeralEncryptionKey =
plugins.encryptedSavedObjects.usingEphemeralEncryptionKey;

Expand Down Expand Up @@ -265,10 +269,14 @@ export class AlertingPlugin {
savedObjects: SavedObjectsServiceStart
): (request: KibanaRequest) => Services {
const { adminClient } = this;
return request => ({
callCluster: adminClient!.asScoped(request).callAsCurrentUser,
savedObjectsClient: savedObjects.getScopedClient(request),
});
return request => {
const caller = adminClient!.asScoped(request).callAsCurrentUser;
return {
callCluster: caller,
savedObjectsClient: savedObjects.getScopedClient(request),
search: this.data!.search.createScopedSearchApi(caller).search,
};
};
}

private spaceIdToNamespace = (spaceId?: string): string | undefined => {
Expand Down
2 changes: 2 additions & 0 deletions x-pack/plugins/alerting/server/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { PluginSetupContract, PluginStartContract } from './plugin';
import { SavedObjectAttributes, SavedObjectsClientContract } from '../../../../src/core/server';
import { Alert, AlertActionParams, ActionGroup } from '../common';
import { AlertsClient } from './alerts_client';
import { ISearchGeneric } from '../../../../src/plugins/data/server';
export * from '../common';

export type State = Record<string, any>;
Expand All @@ -31,6 +32,7 @@ declare module 'src/core/server' {
export interface Services {
callCluster(path: string, opts: any): Promise<any>;
savedObjectsClient: SavedObjectsClientContract;
search: ISearchGeneric;
}

export interface AlertServices extends Services {
Expand Down

0 comments on commit af1e245

Please sign in to comment.