diff --git a/x-pack/plugins/observability/public/components/custom_threshold/components/alert_flyout.tsx b/x-pack/plugins/observability/public/components/custom_threshold/components/alert_flyout.tsx deleted file mode 100644 index 1a90ffc7460c..000000000000 --- a/x-pack/plugins/observability/public/components/custom_threshold/components/alert_flyout.tsx +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one - * or more contributor license agreements. Licensed under the Elastic License - * 2.0; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import React, { useCallback, useContext, useMemo } from 'react'; - -import { OBSERVABILITY_THRESHOLD_RULE_TYPE_ID } from '@kbn/rule-data-utils'; -import { TriggerActionsContext } from './triggers_actions_context'; -import { observabilityRuleCreationValidConsumers } from '../../../../common/constants'; - -interface Props { - visible?: boolean; - setVisible: React.Dispatch>; -} - -export function AlertFlyout(props: Props) { - const { visible, setVisible } = props; - const { triggersActionsUI } = useContext(TriggerActionsContext); - const onCloseFlyout = useCallback(() => setVisible(false), [setVisible]); - const AddAlertFlyout = useMemo( - () => - triggersActionsUI && - triggersActionsUI.getAddRuleFlyout({ - consumer: 'logs', - onClose: onCloseFlyout, - canChangeTrigger: false, - ruleTypeId: OBSERVABILITY_THRESHOLD_RULE_TYPE_ID, - validConsumers: observabilityRuleCreationValidConsumers, - useRuleProducer: true, - }), - [triggersActionsUI, onCloseFlyout] - ); - - return <>{visible && AddAlertFlyout}; -} - -export function PrefilledThresholdAlertFlyout({ onClose }: { onClose(): void }) { - return ; -} diff --git a/x-pack/plugins/observability/public/components/custom_threshold/components/metrics_alert_dropdown.tsx b/x-pack/plugins/observability/public/components/custom_threshold/components/metrics_alert_dropdown.tsx deleted file mode 100644 index 91b97161f78d..000000000000 --- a/x-pack/plugins/observability/public/components/custom_threshold/components/metrics_alert_dropdown.tsx +++ /dev/null @@ -1,191 +0,0 @@ -/* - * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one - * or more contributor license agreements. Licensed under the Elastic License - * 2.0; you may not use this file except in compliance with the Elastic License - * 2.0. - */ - -import { i18n } from '@kbn/i18n'; -import React, { useState, useCallback, useMemo } from 'react'; -import { - EuiPopover, - EuiHeaderLink, - EuiContextMenu, - EuiContextMenuPanelDescriptor, -} from '@elastic/eui'; -import { FormattedMessage } from '@kbn/i18n-react'; -import { useKibana } from '@kbn/kibana-react-plugin/public'; -import { InfraClientStartDeps } from '../types'; -import { PrefilledThresholdAlertFlyout } from './alert_flyout'; - -type VisibleFlyoutType = 'inventory' | 'threshold' | null; - -export function MetricsAlertDropdown() { - const [popoverOpen, setPopoverOpen] = useState(false); - const [visibleFlyoutType, setVisibleFlyoutType] = useState(null); - const uiCapabilities = useKibana().services.application?.capabilities; - const { - services: { observability }, - } = useKibana(); - const canCreateAlerts = useMemo( - () => Boolean(uiCapabilities?.infrastructure?.save), - [uiCapabilities] - ); - - const closeFlyout = useCallback(() => setVisibleFlyoutType(null), [setVisibleFlyoutType]); - - const closePopover = useCallback(() => { - setPopoverOpen(false); - }, [setPopoverOpen]); - - const togglePopover = useCallback(() => { - setPopoverOpen(!popoverOpen); - }, [setPopoverOpen, popoverOpen]); - const infrastructureAlertsPanel = useMemo( - () => ({ - id: 1, - title: i18n.translate( - 'xpack.observability.customThreshold.rule.infrastructureDropdownTitle', - { - defaultMessage: 'Infrastructure rules', - } - ), - items: [ - { - 'data-test-subj': 'inventory-alerts-create-rule', - name: i18n.translate( - 'xpack.observability.customThreshold.rule.createInventoryRuleButton', - { - defaultMessage: 'Create inventory rule', - } - ), - onClick: () => { - closePopover(); - setVisibleFlyoutType('inventory'); - }, - }, - ], - }), - [setVisibleFlyoutType, closePopover] - ); - - const metricsAlertsPanel = useMemo( - () => ({ - id: 2, - title: i18n.translate('xpack.observability.customThreshold.rule.metricsDropdownTitle', { - defaultMessage: 'Metrics rules', - }), - items: [ - { - 'data-test-subj': 'metrics-threshold-alerts-create-rule', - name: i18n.translate( - 'xpack.observability.customThreshold.rule.createThresholdRuleButton', - { - defaultMessage: 'Create threshold rule', - } - ), - onClick: () => { - closePopover(); - setVisibleFlyoutType('threshold'); - }, - }, - ], - }), - [setVisibleFlyoutType, closePopover] - ); - - const manageRulesLinkProps = observability.useRulesLink(); - - const manageAlertsMenuItem = useMemo( - () => ({ - name: i18n.translate('xpack.observability.customThreshold.rule.manageRules', { - defaultMessage: 'Manage rules', - }), - icon: 'tableOfContents', - onClick: manageRulesLinkProps.onClick, - }), - [manageRulesLinkProps] - ); - - const firstPanelMenuItems: EuiContextMenuPanelDescriptor['items'] = useMemo( - () => - canCreateAlerts - ? [ - { - 'data-test-subj': 'inventory-alerts-menu-option', - name: i18n.translate( - 'xpack.observability.customThreshold.rule.infrastructureDropdownMenu', - { - defaultMessage: 'Infrastructure', - } - ), - panel: 1, - }, - { - 'data-test-subj': 'metrics-threshold-alerts-menu-option', - name: i18n.translate('xpack.observability.customThreshold.rule.metricsDropdownMenu', { - defaultMessage: 'Metrics', - }), - panel: 2, - }, - manageAlertsMenuItem, - ] - : [manageAlertsMenuItem], - [canCreateAlerts, manageAlertsMenuItem] - ); - - const panels: EuiContextMenuPanelDescriptor[] = useMemo( - () => - [ - { - id: 0, - title: i18n.translate('xpack.observability.customThreshold.rule.alertDropdownTitle', { - defaultMessage: 'Alerts and rules', - }), - items: firstPanelMenuItems, - }, - ].concat(canCreateAlerts ? [infrastructureAlertsPanel, metricsAlertsPanel] : []), - [infrastructureAlertsPanel, metricsAlertsPanel, firstPanelMenuItems, canCreateAlerts] - ); - return ( - <> - - - - } - isOpen={popoverOpen} - closePopover={closePopover} - > - - - - - ); -} - -interface AlertFlyoutProps { - visibleFlyoutType: VisibleFlyoutType; - onClose(): void; -} - -function AlertFlyout({ visibleFlyoutType, onClose }: AlertFlyoutProps) { - switch (visibleFlyoutType) { - case 'threshold': - return ; - default: - return null; - } -} diff --git a/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.test.tsx b/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.test.tsx index 0f1742469c31..ce1c9527904c 100644 --- a/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.test.tsx +++ b/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.test.tsx @@ -6,16 +6,16 @@ */ import React from 'react'; -import { act } from 'react-dom/test-utils'; -import { QueryClientProvider } from '@tanstack/react-query'; import { dataViewPluginMocks } from '@kbn/data-views-plugin/public/mocks'; import { queryClient } from '@kbn/osquery-plugin/public/query_client'; import { mountWithIntl, nextTick } from '@kbn/test-jest-helpers'; - +import { QueryClientProvider } from '@tanstack/react-query'; +import { act } from 'react-dom/test-utils'; import { Aggregators, Comparator } from '../../../common/custom_threshold_rule/types'; import { useKibana } from '../../utils/kibana_react'; import { kibanaStartMock } from '../../utils/kibana_react.mock'; import Expressions from './custom_threshold_rule_expression'; +import { CustomThresholdPrefillOptions } from './types'; jest.mock('../../utils/kibana_react'); jest.mock('./components/preview_chart/preview_chart', () => ({ @@ -38,7 +38,10 @@ describe('Expression', () => { mockKibana(); }); - async function setup() { + async function setup( + currentOptions?: CustomThresholdPrefillOptions, + customRuleParams?: Record + ) { const ruleParams = { criteria: [], groupBy: undefined, @@ -50,6 +53,11 @@ describe('Expression', () => { language: 'kuery', }, }, + ...customRuleParams, + }; + const metadata = { + currentOptions, + adHocDataViewList: [], }; const wrapper = mountWithIntl( @@ -61,9 +69,7 @@ describe('Expression', () => { errors={{}} setRuleParams={(key, value) => Reflect.set(ruleParams, key, value)} setRuleProperty={() => {}} - metadata={{ - adHocDataViewList: [], - }} + metadata={metadata} dataViews={dataViewMock} onChangeMetaData={jest.fn()} /> @@ -81,6 +87,59 @@ describe('Expression', () => { return { wrapper, update, ruleParams }; } + const updateUseKibanaMock = (mockedIndex: any) => { + const mockedDataView = { + getIndexPattern: () => 'mockedIndexPattern', + getName: () => 'mockedName', + ...mockedIndex, + }; + const mockedSearchSource = { + id: 'data_source', + shouldOverwriteDataViewType: false, + requestStartHandlers: [], + inheritOptions: {}, + history: [], + fields: { + index: mockedIndex, + }, + getField: jest.fn(() => mockedDataView), + setField: jest.fn(), + getSerializedFields: jest.fn().mockReturnValue({ index: mockedIndex }), + dependencies: { + aggs: { + types: {}, + }, + }, + }; + const kibanaMock = kibanaStartMock.startContract(); + useKibanaMock.mockReturnValue({ + ...kibanaMock, + services: { + ...kibanaMock.services, + data: { + dataViews: { + create: jest.fn(), + getDefaultDataView: jest.fn(), + }, + query: { + timefilter: { + timefilter: jest.fn(), + }, + queryString: { + getDefaultQuery: jest.fn(), + }, + }, + search: { + searchSource: { + create: jest.fn(() => mockedSearchSource), + createEmpty: jest.fn(() => mockedSearchSource), + }, + }, + }, + }, + }); + }; + it('should use default metrics', async () => { const { ruleParams } = await setup(); expect(ruleParams.criteria).toEqual([ @@ -99,6 +158,41 @@ describe('Expression', () => { ]); }); + it('should prefill the rule using the context metadata', async () => { + const index = 'changedMockedIndex'; + const currentOptions: CustomThresholdPrefillOptions = { + groupBy: ['host.hostname'], + filterQuery: 'foo', + searchConfiguration: { index }, + criteria: [ + { + metrics: [ + { name: 'A', aggType: Aggregators.AVERAGE, field: 'system.load.1' }, + { name: 'B', aggType: Aggregators.CARDINALITY, field: 'system.cpu.user.pct' }, + ], + }, + ], + }; + + const { ruleParams } = await setup(currentOptions, { searchConfiguration: undefined }); + + expect(ruleParams.groupBy).toEqual(['host.hostname']); + expect(ruleParams.searchConfiguration.query.query).toBe('foo'); + expect(ruleParams.searchConfiguration.index).toBe(index); + expect(ruleParams.criteria).toEqual([ + { + metrics: [ + { name: 'A', aggType: Aggregators.AVERAGE, field: 'system.load.1' }, + { name: 'B', aggType: Aggregators.CARDINALITY, field: 'system.cpu.user.pct' }, + ], + comparator: Comparator.GT, + threshold: [100], + timeSize: 1, + timeUnit: 'm', + }, + ]); + }); + it('should show an error message when searchSource throws an error', async () => { const errorMessage = 'Error in searchSource create'; const kibanaMock = kibanaStartMock.startContract(); @@ -140,49 +234,7 @@ describe('Expression', () => { // We should not provide timeFieldName here to show thresholdRuleDataViewErrorNoTimestamp error // timeFieldName: '@timestamp', }; - const mockedDataView = { - getIndexPattern: () => 'mockedIndexPattern', - getName: () => 'mockedName', - ...mockedIndex, - }; - const mockedSearchSource = { - id: 'data_source', - shouldOverwriteDataViewType: false, - requestStartHandlers: [], - inheritOptions: {}, - history: [], - fields: { - index: mockedIndex, - }, - getField: jest.fn(() => mockedDataView), - dependencies: { - aggs: { - types: {}, - }, - }, - }; - const kibanaMock = kibanaStartMock.startContract(); - useKibanaMock.mockReturnValue({ - ...kibanaMock, - services: { - ...kibanaMock.services, - data: { - dataViews: { - create: jest.fn(), - }, - query: { - timefilter: { - timefilter: jest.fn(), - }, - }, - search: { - searchSource: { - create: jest.fn(() => mockedSearchSource), - }, - }, - }, - }, - }); + updateUseKibanaMock(mockedIndex); const { wrapper } = await setup(); expect( wrapper.find(`[data-test-subj="thresholdRuleDataViewErrorNoTimestamp"]`).first().text() @@ -190,4 +242,19 @@ describe('Expression', () => { 'The selected data view does not have a timestamp field, please select another data view.' ); }); + + it('should use output of getSerializedFields() as searchConfiguration', async () => { + const mockedIndex = { + id: 'c34a7c79-a88b-4b4a-ad19-72f6d24104e4', + title: 'metrics-fake_hosts', + fieldFormatMap: {}, + typeMeta: {}, + timeFieldName: '@timestamp', + }; + updateUseKibanaMock(mockedIndex); + const { ruleParams } = await setup(undefined, { searchConfiguration: undefined }); + expect(ruleParams.searchConfiguration).toEqual({ + index: mockedIndex, + }); + }); }); diff --git a/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.tsx b/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.tsx index 539f8fbf4f58..0df72511ce55 100644 --- a/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.tsx +++ b/x-pack/plugins/observability/public/components/custom_threshold/custom_threshold_rule_expression.tsx @@ -96,14 +96,24 @@ export default function Expressions(props: Props) { let initialSearchConfiguration = ruleParams.searchConfiguration; if (!ruleParams.searchConfiguration || !ruleParams.searchConfiguration.index) { - const newSearchSource = data.search.searchSource.createEmpty(); - newSearchSource.setField('query', data.query.queryString.getDefaultQuery()); - const defaultDataView = await data.dataViews.getDefaultDataView(); - if (defaultDataView) { - newSearchSource.setField('index', defaultDataView); - setDataView(defaultDataView); + if (metadata?.currentOptions?.searchConfiguration) { + initialSearchConfiguration = { + ...metadata.currentOptions.searchConfiguration, + query: { + query: ruleParams.searchConfiguration?.query ?? '', + language: 'kuery', + }, + }; + } else { + const newSearchSource = data.search.searchSource.createEmpty(); + newSearchSource.setField('query', data.query.queryString.getDefaultQuery()); + const defaultDataView = await data.dataViews.getDefaultDataView(); + if (defaultDataView) { + newSearchSource.setField('index', defaultDataView); + setDataView(defaultDataView); + } + initialSearchConfiguration = newSearchSource.getSerializedFields(); } - initialSearchConfiguration = newSearchSource.getSerializedFields(); } try { @@ -151,7 +161,15 @@ export default function Expressions(props: Props) { setTimeSize(ruleParams.criteria[0].timeSize); setTimeUnit(ruleParams.criteria[0].timeUnit); } else { - setRuleParams('criteria', [defaultExpression]); + preFillCriteria(); + } + + if (!ruleParams.filterQuery) { + preFillFilterQuery(); + } + + if (!ruleParams.groupBy) { + preFillGroupBy(); } if (typeof ruleParams.alertOnNoData === 'undefined') { @@ -259,6 +277,42 @@ export default function Expressions(props: Props) { [ruleParams.criteria, setRuleParams] ); + const preFillFilterQuery = useCallback(() => { + const md = metadata; + + if (md && md.currentOptions?.filterQuery) { + setRuleParams('searchConfiguration', { + ...ruleParams.searchConfiguration, + query: { + query: md.currentOptions.filterQuery, + language: 'kuery', + }, + }); + } + }, [metadata, setRuleParams, ruleParams.searchConfiguration]); + + const preFillCriteria = useCallback(() => { + const md = metadata; + if (md?.currentOptions?.criteria?.length) { + setRuleParams( + 'criteria', + md.currentOptions.criteria.map((criterion) => ({ + ...defaultExpression, + ...criterion, + })) + ); + } else { + setRuleParams('criteria', [defaultExpression]); + } + }, [metadata, setRuleParams]); + + const preFillGroupBy = useCallback(() => { + const md = metadata; + if (md && md.currentOptions?.groupBy) { + setRuleParams('groupBy', md.currentOptions.groupBy); + } + }, [metadata, setRuleParams]); + const hasGroupBy = useMemo( () => ruleParams.groupBy && ruleParams.groupBy.length > 0, [ruleParams.groupBy] diff --git a/x-pack/plugins/observability/public/components/custom_threshold/hooks/use_metrics_explorer_data.test.tsx b/x-pack/plugins/observability/public/components/custom_threshold/hooks/use_expression_data.test.tsx similarity index 100% rename from x-pack/plugins/observability/public/components/custom_threshold/hooks/use_metrics_explorer_data.test.tsx rename to x-pack/plugins/observability/public/components/custom_threshold/hooks/use_expression_data.test.tsx diff --git a/x-pack/plugins/observability/public/components/custom_threshold/types.ts b/x-pack/plugins/observability/public/components/custom_threshold/types.ts index dc0ad4eb7162..9753cabbc118 100644 --- a/x-pack/plugins/observability/public/components/custom_threshold/types.ts +++ b/x-pack/plugins/observability/public/components/custom_threshold/types.ts @@ -15,6 +15,7 @@ import { EmbeddableStart } from '@kbn/embeddable-plugin/public'; import { IStorageWrapper } from '@kbn/kibana-utils-plugin/public'; import { LensPublicStart } from '@kbn/lens-plugin/public'; import { ObservabilitySharedPluginStart } from '@kbn/observability-shared-plugin/public'; +import { OsqueryPluginStart } from '@kbn/osquery-plugin/public'; import { SharePluginStart } from '@kbn/share-plugin/public'; import { SpacesPluginStart } from '@kbn/spaces-plugin/public'; import { @@ -28,11 +29,18 @@ import { CustomMetricExpressionParams, BaseMetricExpressionParams, aggType, + ThresholdParams, + MetricExpressionParams, } from '../../../common/custom_threshold_rule/types'; import { ObservabilityPublicStart } from '../../plugin'; +export type CustomThresholdPrefillOptions = Partial< + Omit & { criteria: Array> } +>; + export interface AlertContextMeta { adHocDataViewList: DataView[]; + currentOptions?: CustomThresholdPrefillOptions; } export type MetricExpression = Omit & { @@ -66,7 +74,7 @@ export interface InfraClientStartDeps { lens: LensPublicStart; observability: ObservabilityPublicStart; observabilityShared: ObservabilitySharedPluginStart; - osquery?: unknown; // OsqueryPluginStart; + osquery?: OsqueryPluginStart; share: SharePluginStart; spaces: SpacesPluginStart; storage: IStorageWrapper; diff --git a/x-pack/plugins/translations/translations/fr-FR.json b/x-pack/plugins/translations/translations/fr-FR.json index 53e6407db2a7..549c459b4944 100644 --- a/x-pack/plugins/translations/translations/fr-FR.json +++ b/x-pack/plugins/translations/translations/fr-FR.json @@ -28910,7 +28910,6 @@ "xpack.observability.customThreshold.rule.alertDetailsAppSection.summaryField.rule": "Règle", "xpack.observability.customThreshold.rule.alertDetailsAppSection.thresholdTitle": "Seuil dépassé", "xpack.observability.customThreshold.rule.alertDetailUrlActionVariableDescription": "Lien vers l’affichage de résolution des problèmes d’alerte pour voir plus de contextes et de détails. La chaîne sera vide si server.publicBaseUrl n'est pas configuré.", - "xpack.observability.customThreshold.rule.alertDropdownTitle": "Alertes et règles", "xpack.observability.customThreshold.rule.alertFlyout.addCondition": "Ajouter une condition", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.avg": "Moyenne", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.cardinality": "Cardinalité", @@ -28958,19 +28957,11 @@ "xpack.observability.customThreshold.rule.alerting.threshold.defaultActionMessage": "\\{\\{context.reason\\}\\}\n\n\\{\\{rule.name\\}\\} est actif.\n\n[Voir les détails de l’alerte](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.defaultRecoveryMessage": "\\{\\{rule.name\\}\\} a récupéré.\n\n[Voir les détails de l’alerte](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.noDataFormattedValue": "[AUCUNE DONNÉE]", - "xpack.observability.customThreshold.rule.alertsButton": "Alertes et règles", "xpack.observability.customThreshold.rule.cloudActionVariableDescription": "Objet cloud défini par ECS s'il est disponible dans la source.", "xpack.observability.customThreshold.rule.containerActionVariableDescription": "Objet conteneur défini par ECS s'il est disponible dans la source.", - "xpack.observability.customThreshold.rule.createInventoryRuleButton": "Créer une règle d'inventaire", - "xpack.observability.customThreshold.rule.createThresholdRuleButton": "Créer une règle de seuil", "xpack.observability.customThreshold.rule.groupByKeysActionVariableDescription": "Objet contenant les groupes qui fournissent les données", "xpack.observability.customThreshold.rule.hostActionVariableDescription": "Objet hôte défini par ECS s'il est disponible dans la source.", - "xpack.observability.customThreshold.rule.infrastructureDropdownMenu": "Infrastructure", - "xpack.observability.customThreshold.rule.infrastructureDropdownTitle": "Règles d'infrastructure", "xpack.observability.customThreshold.rule.labelsActionVariableDescription": "Liste d'étiquettes associées avec l'entité sur laquelle l'alerte s'est déclenchée.", - "xpack.observability.customThreshold.rule.manageRules": "Gérer les règles", - "xpack.observability.customThreshold.rule.metricsDropdownMenu": "Indicateurs", - "xpack.observability.customThreshold.rule.metricsDropdownTitle": "Règles d'indicateurs", "xpack.observability.customThreshold.rule.orchestratorActionVariableDescription": "Objet orchestrateur défini par ECS s'il est disponible dans la source.", "xpack.observability.customThreshold.rule.reasonActionVariableDescription": "Une description concise de la raison du signalement", "xpack.observability.customThreshold.rule.schema.invalidFilterQuery": "filterQuery doit être un filtre KQL valide", diff --git a/x-pack/plugins/translations/translations/ja-JP.json b/x-pack/plugins/translations/translations/ja-JP.json index 0262f5fe786e..8ab33bb6186b 100644 --- a/x-pack/plugins/translations/translations/ja-JP.json +++ b/x-pack/plugins/translations/translations/ja-JP.json @@ -28910,7 +28910,6 @@ "xpack.observability.customThreshold.rule.alertDetailsAppSection.summaryField.rule": "ルール", "xpack.observability.customThreshold.rule.alertDetailsAppSection.thresholdTitle": "しきい値を超えました", "xpack.observability.customThreshold.rule.alertDetailUrlActionVariableDescription": "アラートトラブルシューティングビューにリンクして、さらに詳しい状況や詳細を確認できます。server.publicBaseUrlが構成されていない場合は、空の文字列になります。", - "xpack.observability.customThreshold.rule.alertDropdownTitle": "アラートとルール", "xpack.observability.customThreshold.rule.alertFlyout.addCondition": "条件を追加", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.avg": "平均", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.cardinality": "基数", @@ -28958,19 +28957,11 @@ "xpack.observability.customThreshold.rule.alerting.threshold.defaultActionMessage": "\\{\\{context.reason\\}\\}\n\n\\{\\{rule.name\\}\\}はアクティブです。\n\n[アラート詳細を表示](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.defaultRecoveryMessage": "\\{\\{rule.name\\}\\}が回復しました。\n\n[アラート詳細を表示](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.noDataFormattedValue": "[データなし]", - "xpack.observability.customThreshold.rule.alertsButton": "アラートとルール", "xpack.observability.customThreshold.rule.cloudActionVariableDescription": "ソースで使用可能な場合に、ECSで定義されたクラウドオブジェクト。", "xpack.observability.customThreshold.rule.containerActionVariableDescription": "ソースで使用可能な場合に、ECSで定義されたコンテナーオブジェクト。", - "xpack.observability.customThreshold.rule.createInventoryRuleButton": "インベントリルールの作成", - "xpack.observability.customThreshold.rule.createThresholdRuleButton": "しきい値ルールを作成", "xpack.observability.customThreshold.rule.groupByKeysActionVariableDescription": "データを報告しているグループを含むオブジェクト", "xpack.observability.customThreshold.rule.hostActionVariableDescription": "ソースで使用可能な場合に、ECSで定義されたホストオブジェクト。", - "xpack.observability.customThreshold.rule.infrastructureDropdownMenu": "インフラストラクチャー", - "xpack.observability.customThreshold.rule.infrastructureDropdownTitle": "インフラストラクチャールール", "xpack.observability.customThreshold.rule.labelsActionVariableDescription": "このアラートがトリガーされたエンティティに関連付けられたラベルのリスト。", - "xpack.observability.customThreshold.rule.manageRules": "ルールの管理", - "xpack.observability.customThreshold.rule.metricsDropdownMenu": "メトリック", - "xpack.observability.customThreshold.rule.metricsDropdownTitle": "メトリックルール", "xpack.observability.customThreshold.rule.orchestratorActionVariableDescription": "ソースで使用可能な場合に、ECSで定義されたオーケストレーターオブジェクト。", "xpack.observability.customThreshold.rule.reasonActionVariableDescription": "アラートの理由の簡潔な説明", "xpack.observability.customThreshold.rule.schema.invalidFilterQuery": "filterQueryは有効なKQLフィルターでなければなりません", diff --git a/x-pack/plugins/translations/translations/zh-CN.json b/x-pack/plugins/translations/translations/zh-CN.json index fae7979b4b37..d12e87825273 100644 --- a/x-pack/plugins/translations/translations/zh-CN.json +++ b/x-pack/plugins/translations/translations/zh-CN.json @@ -28907,7 +28907,6 @@ "xpack.observability.customThreshold.rule.alertDetailsAppSection.summaryField.rule": "规则", "xpack.observability.customThreshold.rule.alertDetailsAppSection.thresholdTitle": "超出阈值", "xpack.observability.customThreshold.rule.alertDetailUrlActionVariableDescription": "链接到告警故障排除视图获取进一步的上下文和详情。如果未配置 server.publicBaseUrl,这将为空字符串。", - "xpack.observability.customThreshold.rule.alertDropdownTitle": "告警和规则", "xpack.observability.customThreshold.rule.alertFlyout.addCondition": "添加条件", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.avg": "平均值", "xpack.observability.customThreshold.rule.alertFlyout.aggregationText.cardinality": "基数", @@ -28955,19 +28954,11 @@ "xpack.observability.customThreshold.rule.alerting.threshold.defaultActionMessage": "\\{\\{context.reason\\}\\}\n\n\\{\\{rule.name\\}\\} 处于活动状态。\n\n[查看告警详情](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.defaultRecoveryMessage": "\\{\\{rule.name\\}\\} 已恢复。\n\n[查看告警详情](\\{\\{context.alertDetailsUrl\\}\\})\n", "xpack.observability.customThreshold.rule.alerting.threshold.noDataFormattedValue": "[无数据]", - "xpack.observability.customThreshold.rule.alertsButton": "告警和规则", "xpack.observability.customThreshold.rule.cloudActionVariableDescription": "ECS 定义的云对象(如果在源中可用)。", "xpack.observability.customThreshold.rule.containerActionVariableDescription": "ECS 定义的容器对象(如果在源中可用)。", - "xpack.observability.customThreshold.rule.createInventoryRuleButton": "创建库存规则", - "xpack.observability.customThreshold.rule.createThresholdRuleButton": "创建阈值规则", "xpack.observability.customThreshold.rule.groupByKeysActionVariableDescription": "包含正报告数据的组的对象", "xpack.observability.customThreshold.rule.hostActionVariableDescription": "ECS 定义的主机对象(如果在源中可用)。", - "xpack.observability.customThreshold.rule.infrastructureDropdownMenu": "基础设施", - "xpack.observability.customThreshold.rule.infrastructureDropdownTitle": "基础设施规则", "xpack.observability.customThreshold.rule.labelsActionVariableDescription": "与在其上触发此告警的实体关联的标签列表。", - "xpack.observability.customThreshold.rule.manageRules": "管理规则", - "xpack.observability.customThreshold.rule.metricsDropdownMenu": "指标", - "xpack.observability.customThreshold.rule.metricsDropdownTitle": "指标规则", "xpack.observability.customThreshold.rule.orchestratorActionVariableDescription": "ECS 定义的 Orchestrator 对象(如果在源中可用)。", "xpack.observability.customThreshold.rule.reasonActionVariableDescription": "告警原因的简洁描述", "xpack.observability.customThreshold.rule.schema.invalidFilterQuery": "filterQuery 必须是有效的 KQL 筛选",