From 70ece1055fe2623f1821a9ac8081cb0bef058566 Mon Sep 17 00:00:00 2001 From: christineweng <18648970+christineweng@users.noreply.github.com> Date: Thu, 20 Feb 2025 17:00:20 -0600 Subject: [PATCH] [Security Solution] Fix analyzer no data message in flyout when analyzer is not enabled (#211981) ## Summary When an alert does not have analyzer enabled (i.e. no data), the analyzer graph showed "error loading data". This PR added checks if analyzer should be present and added no data message, this is consistent with the analyzer preview. image ### Checklist - [x] Any text added follows [EUI's writing guidelines](https://elastic.github.io/eui/#/guidelines/writing), uses sentence case text and includes [i18n support](https://github.com/elastic/kibana/blob/main/src/platform/packages/shared/kbn-i18n/README.md) - [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 - [x] The PR description includes the appropriate Release Notes section, and the correct `release_note:*` label is applied per the [guidelines](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process) --- .../translations/translations/fr-FR.json | 1 - .../translations/translations/ja-JP.json | 1 - .../translations/translations/zh-CN.json | 1 - .../left/components/analyze_graph.test.tsx | 28 ++++++++++ .../left/components/analyze_graph.tsx | 13 ++++- .../components/analyzer_preview_container.tsx | 53 +++++++++++-------- 6 files changed, 69 insertions(+), 28 deletions(-) diff --git a/x-pack/platform/plugins/private/translations/translations/fr-FR.json b/x-pack/platform/plugins/private/translations/translations/fr-FR.json index d3322f1c0c511..2cb95a100463c 100644 --- a/x-pack/platform/plugins/private/translations/translations/fr-FR.json +++ b/x-pack/platform/plugins/private/translations/translations/fr-FR.json @@ -37915,7 +37915,6 @@ "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.analyzerPreviewTitle": "Aperçu de l'analyseur", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.errorDescription": "Une erreur empêche l'analyse de cette alerte.", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.loadingAriaLabel": "aperçu de l'analyseur", - "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataDescription": "Vous pouvez uniquement visualiser les événements déclenchés par les hôtes configurés avec l'intégration Elastic Defend ou les données {sysmon} provenant de {winlogbeat}. Pour en savoir plus, consultez {link}.", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataLinkText": "Visualiser l'analyseur d'événement", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.treeViewAriaLabel": "Aperçu de l'analyseur", "xpack.securitySolution.flyout.right.visualizations.assignees.popoverTooltip": "Assigner une alerte", diff --git a/x-pack/platform/plugins/private/translations/translations/ja-JP.json b/x-pack/platform/plugins/private/translations/translations/ja-JP.json index 9c3b79be6b06b..0082247b82e70 100644 --- a/x-pack/platform/plugins/private/translations/translations/ja-JP.json +++ b/x-pack/platform/plugins/private/translations/translations/ja-JP.json @@ -37775,7 +37775,6 @@ "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.analyzerPreviewTitle": "アナライザープレビュー", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.errorDescription": "エラーが発生したため、このアラートを分析できません。", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.loadingAriaLabel": "アナライザープレビュー", - "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataDescription": "Elastic Defend統合で構成されたホストまたは{winlogbeat}の{sysmon}データによってトリガーされたイベントのみを可視化できます。詳細については、{link}を参照してください。", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataLinkText": "ビジュアルイベントアナライザー", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.treeViewAriaLabel": "アナライザープレビュー", "xpack.securitySolution.flyout.right.visualizations.assignees.popoverTooltip": "アラートの割り当て", diff --git a/x-pack/platform/plugins/private/translations/translations/zh-CN.json b/x-pack/platform/plugins/private/translations/translations/zh-CN.json index 0edea0d7c6b11..8e5e3514bb8f2 100644 --- a/x-pack/platform/plugins/private/translations/translations/zh-CN.json +++ b/x-pack/platform/plugins/private/translations/translations/zh-CN.json @@ -37214,7 +37214,6 @@ "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.analyzerPreviewTitle": "分析器预览", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.errorDescription": "出现错误,无法分析此告警。", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.loadingAriaLabel": "分析器预览", - "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataDescription": "您只能可视化由使用 Elastic Defend 集成或来自 {winlogbeat} 的任何 {sysmon} 数据配置的主机触发的事件。请参阅 {link} 了解更多信息。", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.noDataLinkText": "可视化事件分析器", "xpack.securitySolution.flyout.right.visualizations.analyzerPreview.treeViewAriaLabel": "分析器预览", "xpack.securitySolution.flyout.right.visualizations.assignees.popoverTooltip": "分配告警", diff --git a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.test.tsx b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.test.tsx index fc3cb1aba8d36..58b96f19d919f 100644 --- a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.test.tsx +++ b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.test.tsx @@ -17,6 +17,7 @@ import { ANALYZER_GRAPH_TEST_ID } from './test_ids'; import { useWhichFlyout } from '../../shared/hooks/use_which_flyout'; import { mockFlyoutApi } from '../../shared/mocks/mock_flyout_context'; import { DocumentDetailsAnalyzerPanelKey } from '../../shared/constants/panel_keys'; +import { useIsInvestigateInResolverActionEnabled } from '../../../../detections/components/alerts_table/timeline_actions/investigate_in_resolver'; jest.mock('react-router-dom', () => { const actual = jest.requireActual('react-router-dom'); @@ -25,6 +26,10 @@ jest.mock('react-router-dom', () => { jest.mock('@kbn/expandable-flyout'); jest.mock('../../../../resolver/view/use_resolver_query_params_cleaner'); jest.mock('../../shared/hooks/use_which_flyout'); +jest.mock( + '../../../../detections/components/alerts_table/timeline_actions/investigate_in_resolver' +); + const mockUseWhichFlyout = useWhichFlyout as jest.Mock; const FLYOUT_KEY = 'securitySolution'; @@ -38,6 +43,9 @@ jest.mock('react-redux', () => { }; }); +const NO_ANALYZER_MESSAGE = + 'You can only visualize events triggered by hosts configured with the Elastic Defend integration or any sysmon data from winlogbeat. Refer to Visual event analyzer(external, opens in a new tab or window) for more information.'; + describe('', () => { beforeEach(() => { mockUseWhichFlyout.mockReturnValue(FLYOUT_KEY); @@ -45,6 +53,7 @@ describe('', () => { }); it('renders analyzer graph correctly', () => { + (useIsInvestigateInResolverActionEnabled as jest.Mock).mockReturnValue(true); const contextValue = { eventId: 'eventId', scopeId: TableId.test, @@ -60,7 +69,26 @@ describe('', () => { expect(wrapper.getByTestId(ANALYZER_GRAPH_TEST_ID)).toBeInTheDocument(); }); + it('renders no data message when analyzer is not enabled', () => { + (useIsInvestigateInResolverActionEnabled as jest.Mock).mockReturnValue(false); + const contextValue = { + eventId: 'eventId', + scopeId: TableId.test, + dataAsNestedObject: {}, + } as unknown as DocumentDetailsContext; + + const { container } = render( + + + + + + ); + expect(container).toHaveTextContent(NO_ANALYZER_MESSAGE); + }); + it('clicking view button should open details panel in preview', () => { + (useIsInvestigateInResolverActionEnabled as jest.Mock).mockReturnValue(true); const contextValue = { eventId: 'eventId', scopeId: TableId.test, diff --git a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.tsx b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.tsx index 253e51786ff14..d07ca9f53325b 100644 --- a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.tsx +++ b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/left/components/analyze_graph.tsx @@ -9,6 +9,7 @@ import type { FC } from 'react'; import React, { useMemo, useCallback } from 'react'; import { useExpandableFlyoutApi } from '@kbn/expandable-flyout'; import { i18n } from '@kbn/i18n'; +import { EuiPanel } from '@elastic/eui'; import { useWhichFlyout } from '../../shared/hooks/use_which_flyout'; import { useDocumentDetailsContext } from '../../shared/context'; import { ANALYZER_GRAPH_TEST_ID } from './test_ids'; @@ -16,6 +17,8 @@ import { Resolver } from '../../../../resolver/view'; import { useTimelineDataFilters } from '../../../../timelines/containers/use_timeline_data_filters'; import { isActiveTimeline } from '../../../../helpers'; import { DocumentDetailsAnalyzerPanelKey } from '../../shared/constants/panel_keys'; +import { useIsInvestigateInResolverActionEnabled } from '../../../../detections/components/alerts_table/timeline_actions/investigate_in_resolver'; +import { AnalyzerPreviewNoDataMessage } from '../../right/components/analyzer_preview_container'; export const ANALYZE_GRAPH_ID = 'analyze_graph'; @@ -34,7 +37,9 @@ export const ANALYZER_PREVIEW_BANNER = { * Analyzer graph view displayed in the document details expandable flyout left section under the Visualize tab */ export const AnalyzeGraph: FC = () => { - const { eventId, scopeId } = useDocumentDetailsContext(); + const { eventId, scopeId, dataAsNestedObject } = useDocumentDetailsContext(); + const isEnabled = useIsInvestigateInResolverActionEnabled(dataAsNestedObject); + const key = useWhichFlyout() ?? 'memory'; const { from, to, shouldUpdate, selectedPatterns } = useTimelineDataFilters( isActiveTimeline(scopeId) @@ -52,7 +57,7 @@ export const AnalyzeGraph: FC = () => { }); }, [openPreviewPanel, key, scopeId]); - return ( + return isEnabled ? (
{ showPanelOnClick={onClick} />
+ ) : ( + + + ); }; diff --git a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/right/components/analyzer_preview_container.tsx b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/right/components/analyzer_preview_container.tsx index 145693eccf551..6db6ed0583872 100644 --- a/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/right/components/analyzer_preview_container.tsx +++ b/x-pack/solutions/security/plugins/security_solution/public/flyout/document_details/right/components/analyzer_preview_container.tsx @@ -120,31 +120,38 @@ export const AnalyzerPreviewContainer: React.FC = () => { }} data-test-subj={ANALYZER_PREVIEW_TEST_ID} > - {isEnabled ? ( - - ) : ( - {'sysmon'}, - winlogbeat: {'winlogbeat'}, - link: ( - - - - ), - }} - /> - )} + {isEnabled ? : } ); }; AnalyzerPreviewContainer.displayName = 'AnalyzerPreviewContainer'; + +/** + * No data message for the analyzer preview. + */ +export const AnalyzerPreviewNoDataMessage: React.FC = () => { + return ( + {'sysmon'}, + winlogbeat: {'winlogbeat'}, + link: ( + + + + ), + }} + /> + ); +}; + +AnalyzerPreviewNoDataMessage.displayName = 'AnalyzerPreviewNoDataMessage';