diff --git a/packages/kbn-alerts-as-data-utils/src/schemas/generated/observability_uptime_schema.ts b/packages/kbn-alerts-as-data-utils/src/schemas/generated/observability_uptime_schema.ts index 6a746f722d612..8770b70402d08 100644 --- a/packages/kbn-alerts-as-data-utils/src/schemas/generated/observability_uptime_schema.ts +++ b/packages/kbn-alerts-as-data-utils/src/schemas/generated/observability_uptime_schema.ts @@ -88,6 +88,7 @@ const ObservabilityUptimeAlertOptional = rt.partial({ value: schemaStringArray, }) ), + labels: schemaUnknown, 'location.id': schemaStringArray, 'location.name': schemaStringArray, 'monitor.id': schemaString, @@ -97,6 +98,7 @@ const ObservabilityUptimeAlertOptional = rt.partial({ 'monitor.type': schemaString, 'observer.geo.name': schemaStringArray, 'observer.name': schemaStringArray, + 'service.name': schemaString, 'tls.server.hash.sha256': schemaString, 'tls.server.x509.issuer.common_name': schemaString, 'tls.server.x509.not_after': schemaDate, diff --git a/x-pack/plugins/alerting/server/integration_tests/__snapshots__/alert_as_data_fields.test.ts.snap b/x-pack/plugins/alerting/server/integration_tests/__snapshots__/alert_as_data_fields.test.ts.snap index 478957afb1d66..072d8c59a53ff 100644 --- a/x-pack/plugins/alerting/server/integration_tests/__snapshots__/alert_as_data_fields.test.ts.snap +++ b/x-pack/plugins/alerting/server/integration_tests/__snapshots__/alert_as_data_fields.test.ts.snap @@ -9851,6 +9851,10 @@ Object { "required": false, "type": "keyword", }, + "labels": Object { + "required": false, + "type": "object", + }, "location.id": Object { "array": true, "required": false, @@ -9892,6 +9896,10 @@ Object { "required": false, "type": "keyword", }, + "service.name": Object { + "required": false, + "type": "keyword", + }, "tls.server.hash.sha256": Object { "required": false, "type": "keyword", @@ -9983,6 +9991,10 @@ Object { "required": false, "type": "keyword", }, + "labels": Object { + "required": false, + "type": "object", + }, "location.id": Object { "array": true, "required": false, @@ -10024,6 +10036,10 @@ Object { "required": false, "type": "keyword", }, + "service.name": Object { + "required": false, + "type": "keyword", + }, "tls.server.hash.sha256": Object { "required": false, "type": "keyword", @@ -10115,6 +10131,10 @@ Object { "required": false, "type": "keyword", }, + "labels": Object { + "required": false, + "type": "object", + }, "location.id": Object { "array": true, "required": false, @@ -10156,6 +10176,10 @@ Object { "required": false, "type": "keyword", }, + "service.name": Object { + "required": false, + "type": "keyword", + }, "tls.server.hash.sha256": Object { "required": false, "type": "keyword", @@ -10247,6 +10271,10 @@ Object { "required": false, "type": "keyword", }, + "labels": Object { + "required": false, + "type": "object", + }, "location.id": Object { "array": true, "required": false, @@ -10288,6 +10316,10 @@ Object { "required": false, "type": "keyword", }, + "service.name": Object { + "required": false, + "type": "keyword", + }, "tls.server.hash.sha256": Object { "required": false, "type": "keyword", @@ -10385,6 +10417,10 @@ Object { "required": false, "type": "keyword", }, + "labels": Object { + "required": false, + "type": "object", + }, "location.id": Object { "array": true, "required": false, @@ -10426,6 +10462,10 @@ Object { "required": false, "type": "keyword", }, + "service.name": Object { + "required": false, + "type": "keyword", + }, "tls.server.hash.sha256": Object { "required": false, "type": "keyword", diff --git a/x-pack/plugins/observability_solution/synthetics/common/field_names.ts b/x-pack/plugins/observability_solution/synthetics/common/field_names.ts index 7b590b3a828a7..e7f8e83d73b4b 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/field_names.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/field_names.ts @@ -12,6 +12,7 @@ export const MONITOR_TYPE = 'monitor.type'; export const URL_FULL = 'url.full'; export const URL_PORT = 'url.port'; export const OBSERVER_NAME = 'observer.name'; +export const SERVICE_NAME = 'service.name'; export const OBSERVER_GEO_NAME = 'observer.geo.name'; export const ERROR_MESSAGE = 'error.message'; export const STATE_ID = 'monitor.state.id'; diff --git a/x-pack/plugins/observability_solution/synthetics/common/requests/get_certs_request_body.ts b/x-pack/plugins/observability_solution/synthetics/common/requests/get_certs_request_body.ts index fa1bd9eafad32..f151192a730ed 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/requests/get_certs_request_body.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/requests/get_certs_request_body.ts @@ -147,6 +147,10 @@ export const getCertsRequestBody = ({ 'tls.server.hash.sha256', 'tls.server.x509.not_after', 'tls.server.x509.not_before', + 'service', + 'labels', + 'tags', + 'error.message', ], collapse: { field: 'tls.server.hash.sha256', @@ -207,11 +211,17 @@ export const processCertsResult = (result: CertificatesResults): CertResult => { not_before: notBefore, common_name: commonName, monitorName: ping?.monitor?.name, + monitorId: ping?.monitor?.id, + serviceName: ping?.service?.name, configId: ping.config_id!, monitorUrl: ping?.url?.full, + labels: ping?.labels, + tags: ping?.tags, '@timestamp': ping['@timestamp'], monitorType: ping?.monitor?.type, + locationId: ping?.observer?.name, locationName: ping?.observer?.geo?.name, + errorMessage: ping?.error?.message, }; }); const total = result.aggregations?.total?.value ?? 0; diff --git a/x-pack/plugins/observability_solution/synthetics/common/rules/synthetics_rule_field_map.ts b/x-pack/plugins/observability_solution/synthetics/common/rules/synthetics_rule_field_map.ts index 79d83359132dc..f82f44ba2d24d 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/rules/synthetics_rule_field_map.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/rules/synthetics_rule_field_map.ts @@ -101,4 +101,12 @@ export const syntheticsRuleFieldMap: FieldMap = { type: 'keyword', required: false, }, + 'service.name': { + type: 'keyword', + required: false, + }, + labels: { + type: 'object', + required: false, + }, } as const; diff --git a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/certs.ts b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/certs.ts index 1e98fcb85794f..4fe14a54c0d66 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/certs.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/certs.ts @@ -43,10 +43,16 @@ export const CertType = t.intersection([ issuer: t.string, sha1: t.string, monitorName: t.string, + monitorId: t.string, monitorType: t.string, monitorUrl: t.string, + locationId: t.string, locationName: t.string, '@timestamp': t.string, + serviceName: t.string, + errorMessage: t.string, + labels: t.record(t.string, t.string), + tags: t.array(t.string), }), ]); diff --git a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/monitor_management/synthetics_overview_status.ts b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/monitor_management/synthetics_overview_status.ts index 6f806d0995543..06c877da7c562 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/monitor_management/synthetics_overview_status.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/monitor_management/synthetics_overview_status.ts @@ -27,6 +27,10 @@ export const OverviewPingCodec = t.intersection([ t.partial({ error: PingErrorType, tags: t.array(t.string), + service: t.type({ + name: t.string, + }), + labels: t.record(t.string, t.string), }), ]); diff --git a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/ping/ping.ts b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/ping/ping.ts index 073a00e5665df..7234387d8561b 100644 --- a/x-pack/plugins/observability_solution/synthetics/common/runtime_types/ping/ping.ts +++ b/x-pack/plugins/observability_solution/synthetics/common/runtime_types/ping/ping.ts @@ -242,6 +242,7 @@ export const PingType = t.intersection([ type: t.string, dataset: t.string, }), + labels: t.record(t.string, t.string), }), ]); diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/common.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/common.ts index c1bf18e18e90b..eea917730ac29 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/common.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/common.ts @@ -334,6 +334,10 @@ export const getDefaultRecoveredSummary = ({ name: hit['monitor.name'], type: hit['monitor.type'], }, + service: { + name: hit['service.name'], + }, + labels: hit.labels, config_id: configId, observer: { geo: { diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/message_utils.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/message_utils.ts index a0a14ddaebfed..812a900667cf7 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/message_utils.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/message_utils.ts @@ -23,6 +23,7 @@ import { ERROR_MESSAGE, AGENT_NAME, STATE_ID, + SERVICE_NAME, } from '../../../common/field_names'; import { OverviewPing } from '../../../common/runtime_types'; import { UNNAMED_LOCATION } from '../../../common/constants'; @@ -36,6 +37,7 @@ export const getMonitorAlertDocument = ( [MONITOR_ID]: monitorSummary.monitorId, [MONITOR_TYPE]: monitorSummary.monitorType, [MONITOR_NAME]: monitorSummary.monitorName, + [SERVICE_NAME]: monitorSummary.serviceName, [URL_FULL]: monitorSummary.monitorUrl, [OBSERVER_GEO_NAME]: locationNames, [OBSERVER_NAME]: locationIds, @@ -45,6 +47,7 @@ export const getMonitorAlertDocument = ( [STATE_ID]: monitorSummary.stateId, 'location.id': locationIds, 'location.name': locationNames, + labels: monitorSummary.labels, configId: monitorSummary.configId, 'kibana.alert.evaluation.threshold': monitorSummary.downThreshold, 'kibana.alert.evaluation.value': @@ -112,6 +115,8 @@ export const getMonitorSummary = ({ monitorName, monitorType: typeToLabelMap[monitorInfo.monitor?.type] || monitorInfo.monitor?.type, lastErrorMessage: monitorInfo.error?.message!, + serviceName: monitorInfo.service?.name, + labels: monitorInfo.labels, locationName: formattedLocationName, locationNames: formattedLocationName, hostName: monitorInfo.agent?.name!, diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/queries/query_monitor_status_alert.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/queries/query_monitor_status_alert.ts index 965c30d9c33ae..1e3453872297c 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/queries/query_monitor_status_alert.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/queries/query_monitor_status_alert.ts @@ -31,6 +31,8 @@ const fields = [ 'url', 'state', 'tags', + 'service', + 'labels', ]; type StatusConfigs = Record; diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/types.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/types.ts index 3190881d728c4..82294e55c08fc 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/types.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/status_rule/types.ts @@ -57,6 +57,7 @@ export interface MonitorSummaryStatusRule { locationId: string; monitorType: string; monitorName: string; + serviceName?: string; locationName: string; locationNames: string; monitorUrlLabel: string; @@ -69,4 +70,5 @@ export interface MonitorSummaryStatusRule { stateId?: string; lastErrorMessage?: string; timestamp: string; + labels?: Record; } diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/message_utils.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/message_utils.ts index 3f0650f12ee8b..15a6f093becd9 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/message_utils.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/message_utils.ts @@ -16,11 +16,29 @@ import { import { i18n } from '@kbn/i18n'; import { PublicAlertsClient } from '@kbn/alerting-plugin/server/alerts_client/types'; import { ObservabilityUptimeAlert } from '@kbn/alerts-as-data-utils'; +import { ALERT_REASON, ALERT_UUID } from '@kbn/rule-data-utils'; import { TLSLatestPing } from './tls_rule_executor'; import { ALERT_DETAILS_URL } from '../action_variables'; import { Cert } from '../../../common/runtime_types'; import { tlsTranslations } from '../translations'; import { MonitorStatusActionGroup } from '../../../common/constants/synthetics_alerts'; +import { + CERT_COMMON_NAME, + CERT_HASH_SHA256, + CERT_ISSUER_NAME, + CERT_VALID_NOT_AFTER, + CERT_VALID_NOT_BEFORE, + ERROR_MESSAGE, + MONITOR_ID, + MONITOR_NAME, + MONITOR_TYPE, + OBSERVER_GEO_NAME, + OBSERVER_NAME, + SERVICE_NAME, + URL_FULL, +} from '../../../common/field_names'; +import { generateAlertMessage } from '../common'; +import { TlsTranslations } from '../../../common/rules/synthetics/translations'; interface TLSContent { summary: string; status?: string; @@ -55,6 +73,8 @@ const getValidAfter = (notAfter?: string): TLSContent => { }; }; +export type CertSummary = ReturnType; + export const getCertSummary = (cert: Cert, expirationThreshold: number, ageThreshold: number) => { const isExpiring = new Date(cert.not_after ?? '').valueOf() < expirationThreshold; const isAging = new Date(cert.not_before ?? '').valueOf() < ageThreshold; @@ -74,13 +94,42 @@ export const getCertSummary = (cert: Cert, expirationThreshold: number, ageThres commonName: cert.common_name ?? '', issuer: cert.issuer ?? '', monitorName: cert.monitorName, + monitorId: cert.configId, + serviceName: cert.serviceName, monitorType: cert.monitorType, + locationId: cert.locationId, locationName: cert.locationName, monitorUrl: cert.monitorUrl, configId: cert.configId, + monitorTags: cert.tags, + errorMessage: cert.errorMessage, + labels: cert.labels, }; }; +export const getTLSAlertDocument = (cert: Cert, monitorSummary: CertSummary, uuid: string) => ({ + [CERT_COMMON_NAME]: cert.common_name, + [CERT_ISSUER_NAME]: cert.issuer, + [CERT_VALID_NOT_AFTER]: cert.not_after, + [CERT_VALID_NOT_BEFORE]: cert.not_before, + [CERT_HASH_SHA256]: cert.sha256, + [ALERT_UUID]: uuid, + [ALERT_REASON]: generateAlertMessage(TlsTranslations.defaultActionMessage, monitorSummary), + [MONITOR_ID]: monitorSummary.monitorId, + [MONITOR_TYPE]: monitorSummary.monitorType, + [MONITOR_NAME]: monitorSummary.monitorName, + [SERVICE_NAME]: monitorSummary.serviceName, + [URL_FULL]: monitorSummary.monitorUrl, + [OBSERVER_GEO_NAME]: monitorSummary.locationName ? [monitorSummary.locationName] : [], + [OBSERVER_NAME]: monitorSummary.locationId ? [monitorSummary.locationId] : [], + [ERROR_MESSAGE]: monitorSummary.errorMessage, + 'location.id': monitorSummary.locationId ? [monitorSummary.locationId] : [], + 'location.name': monitorSummary.locationName ? [monitorSummary.locationName] : [], + labels: cert.labels, + configId: monitorSummary.configId, + 'monitor.tags': monitorSummary.monitorTags ?? [], +}); + export const setTLSRecoveredAlertsContext = async ({ alertsClient, basePath, diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/tls_rule.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/tls_rule.ts index 1339aeac89ad3..5f8fc43c5d91c 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/tls_rule.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/tls_rule/tls_rule.ts @@ -14,28 +14,19 @@ import { AlertsClientError, } from '@kbn/alerting-plugin/server'; import { asyncForEach } from '@kbn/std'; -import { ALERT_REASON, ALERT_UUID } from '@kbn/rule-data-utils'; import { getAlertDetailsUrl, observabilityPaths } from '@kbn/observability-plugin/common'; import { schema } from '@kbn/config-schema'; import { ObservabilityUptimeAlert } from '@kbn/alerts-as-data-utils'; import { syntheticsRuleFieldMap } from '../../../common/rules/synthetics_rule_field_map'; import { SyntheticsPluginsSetupDependencies, SyntheticsServerSetup } from '../../types'; -import { TlsTranslations } from '../../../common/rules/synthetics/translations'; -import { - CERT_COMMON_NAME, - CERT_HASH_SHA256, - CERT_ISSUER_NAME, - CERT_VALID_NOT_AFTER, - CERT_VALID_NOT_BEFORE, -} from '../../../common/field_names'; -import { getCertSummary, setTLSRecoveredAlertsContext } from './message_utils'; +import { getCertSummary, getTLSAlertDocument, setTLSRecoveredAlertsContext } from './message_utils'; import { SyntheticsCommonState } from '../../../common/runtime_types/alert_rules/common'; import { TLSRuleExecutor } from './tls_rule_executor'; import { SYNTHETICS_ALERT_RULE_TYPES, TLS_CERTIFICATE, } from '../../../common/constants/synthetics_alerts'; -import { generateAlertMessage, SyntheticsRuleTypeAlertDefinition, updateState } from '../common'; +import { SyntheticsRuleTypeAlertDefinition, updateState } from '../common'; import { ALERT_DETAILS_URL, getActionVariables } from '../action_variables'; import { SyntheticsMonitorClient } from '../../synthetics_service/synthetics_monitor/synthetics_monitor_client'; import { TLSParams } from '../../../common/runtime_types/alerts/tls'; @@ -119,15 +110,7 @@ export const registerSyntheticsTLSCheckRule = ( state: { ...updateState(ruleState, foundCerts), ...summary }, }); - const payload = { - [CERT_COMMON_NAME]: cert.common_name, - [CERT_ISSUER_NAME]: cert.issuer, - [CERT_VALID_NOT_AFTER]: cert.not_after, - [CERT_VALID_NOT_BEFORE]: cert.not_before, - [CERT_HASH_SHA256]: cert.sha256, - [ALERT_UUID]: uuid, - [ALERT_REASON]: generateAlertMessage(TlsTranslations.defaultActionMessage, summary), - }; + const payload = getTLSAlertDocument(cert, summary, uuid); const context = { [ALERT_DETAILS_URL]: await getAlertDetailsUrl(basePath, spaceId, uuid), diff --git a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/translations.ts b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/translations.ts index 37a4cd1e12e97..40017b00646f1 100644 --- a/x-pack/plugins/observability_solution/synthetics/server/alert_rules/translations.ts +++ b/x-pack/plugins/observability_solution/synthetics/server/alert_rules/translations.ts @@ -124,6 +124,24 @@ export const commonMonitorStateI18: Array<{ } ), }, + { + name: 'serviceName', + description: i18n.translate( + 'xpack.synthetics.alertRules.monitorStatus.actionVariables.state.serviceName', + { + defaultMessage: 'Service name associated with the monitor.', + } + ), + }, + { + name: 'labels', + description: i18n.translate( + 'xpack.synthetics.alertRules.monitorStatus.actionVariables.state.labels', + { + defaultMessage: 'Labels associated with the monitor.', + } + ), + }, ]; export const commonStateTranslations = [ diff --git a/x-pack/plugins/observability_solution/uptime/common/rules/uptime_rule_field_map.ts b/x-pack/plugins/observability_solution/uptime/common/rules/uptime_rule_field_map.ts index 3b2da879c5288..6e0f73e183462 100644 --- a/x-pack/plugins/observability_solution/uptime/common/rules/uptime_rule_field_map.ts +++ b/x-pack/plugins/observability_solution/uptime/common/rules/uptime_rule_field_map.ts @@ -101,4 +101,12 @@ export const uptimeRuleFieldMap: FieldMap = { type: 'keyword', required: false, }, + 'service.name': { + type: 'keyword', + required: false, + }, + labels: { + type: 'object', + required: false, + }, } as const; diff --git a/x-pack/test/rule_registry/security_and_spaces/tests/basic/get_browser_fields_by_feature_id.ts b/x-pack/test/rule_registry/security_and_spaces/tests/basic/get_browser_fields_by_feature_id.ts index f922371edc492..352ff0188b015 100644 --- a/x-pack/test/rule_registry/security_and_spaces/tests/basic/get_browser_fields_by_feature_id.ts +++ b/x-pack/test/rule_registry/security_and_spaces/tests/basic/get_browser_fields_by_feature_id.ts @@ -55,6 +55,7 @@ export default ({ getService }: FtrProviderContext) => { 'kibana', 'observer', 'orchestrator', + 'service', 'tls', 'url', ]); @@ -80,6 +81,7 @@ export default ({ getService }: FtrProviderContext) => { 'monitor', 'observer', 'orchestrator', + 'service', 'tls', 'url', ]);