mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 17:59:23 -04:00
[ML] AIOps: Fix to not run log rate analysis twice when no spike/dip detected. (#180980)
## Summary Part of #172981. This fixes to not run log rate analysis twice when no spike/dip detected and a user needs to adapt the initial selection. When a user clicks in an area of the histogram chart that's not a highlighted change point, the click will just trigger the baseline/deviation time range selection, but it will not automatically run the analysis. Instead, an updated prompt is shown below the chart that explains that the baseline/deviation can be adjusted via dragging and the analysis can be run via the button below that description. Initial view after loading the page: <img width="1040" alt="image" src="90e8c390
-af2a-45e2-8d11-cfd42285200b"> User clicked in an area that's not covered by the highlighted change point: <img width="1026" alt="image" src="050a07e0
-c5e6-4639-a854-83fae10b125b"> ### Checklist Delete any items that are not applicable to this PR. - [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/packages/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] This was checked for breaking API changes and was [labeled appropriately](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process)
This commit is contained in:
parent
87c0451f91
commit
6fdcd8d7b8
34 changed files with 312 additions and 81 deletions
|
@ -9,7 +9,15 @@ export { DualBrush, DualBrushAnnotation } from './src/dual_brush';
|
|||
export { ProgressControls } from './src/progress_controls';
|
||||
export {
|
||||
DocumentCountChart,
|
||||
DocumentCountChartWithAutoAnalysisStart,
|
||||
type BrushSettings,
|
||||
type BrushSelectionUpdateHandler,
|
||||
} from './src/document_count_chart';
|
||||
export type { DocumentCountChartProps } from './src/document_count_chart';
|
||||
export {
|
||||
useLogRateAnalysisStateContext,
|
||||
LogRateAnalysisStateProvider,
|
||||
type GroupTableItem,
|
||||
type GroupTableItemGroup,
|
||||
type TableItemAction,
|
||||
} from './src/log_rate_analysis_state_provider';
|
||||
|
|
|
@ -40,6 +40,8 @@ import type { FieldFormatsStart } from '@kbn/field-formats-plugin/public';
|
|||
|
||||
import { DualBrush, DualBrushAnnotation } from '../..';
|
||||
|
||||
import { useLogRateAnalysisStateContext } from '../log_rate_analysis_state_provider';
|
||||
|
||||
import { BrushBadge } from './brush_badge';
|
||||
|
||||
declare global {
|
||||
|
@ -87,6 +89,11 @@ export type BrushSelectionUpdateHandler = (
|
|||
logRateAnalysisType: LogRateAnalysisType
|
||||
) => void;
|
||||
|
||||
/**
|
||||
* Callback to set the autoRunAnalysis flag
|
||||
*/
|
||||
type SetAutoRunAnalysisFn = (isAutoRun: boolean) => void;
|
||||
|
||||
/**
|
||||
* Props for document count chart
|
||||
*/
|
||||
|
@ -118,9 +125,11 @@ export interface DocumentCountChartProps {
|
|||
chartPointsSplitLabel: string;
|
||||
/** Whether or not brush has been reset */
|
||||
isBrushCleared: boolean;
|
||||
/** Callback to set the autoRunAnalysis flag */
|
||||
setAutoRunAnalysis?: SetAutoRunAnalysisFn;
|
||||
/** Timestamp for start of initial analysis */
|
||||
autoAnalysisStart?: number | WindowParameters;
|
||||
/** Optional style to override bar chart */
|
||||
/** Optional style to override bar chart */
|
||||
barStyleAccessor?: BarStyleAccessor;
|
||||
/** Optional color override for the default bar color for charts */
|
||||
barColorOverride?: string;
|
||||
|
@ -181,6 +190,7 @@ export const DocumentCountChart: FC<DocumentCountChartProps> = (props) => {
|
|||
interval,
|
||||
chartPointsSplitLabel,
|
||||
isBrushCleared,
|
||||
setAutoRunAnalysis,
|
||||
autoAnalysisStart,
|
||||
barColorOverride,
|
||||
barStyleAccessor,
|
||||
|
@ -305,6 +315,17 @@ export const DocumentCountChart: FC<DocumentCountChartProps> = (props) => {
|
|||
windowParameters === undefined &&
|
||||
adjustedChartPoints !== undefined
|
||||
) {
|
||||
if (setAutoRunAnalysis) {
|
||||
const autoRun =
|
||||
typeof startRange !== 'number' ||
|
||||
(typeof startRange === 'number' &&
|
||||
changePoint !== undefined &&
|
||||
startRange >= changePoint.startTs &&
|
||||
startRange <= changePoint.endTs);
|
||||
|
||||
setAutoRunAnalysis(autoRun);
|
||||
}
|
||||
|
||||
const wp = getWindowParametersForTrigger(
|
||||
startRange,
|
||||
interval,
|
||||
|
@ -333,6 +354,7 @@ export const DocumentCountChart: FC<DocumentCountChartProps> = (props) => {
|
|||
timeRangeLatest,
|
||||
snapTimestamps,
|
||||
originalWindowParameters,
|
||||
setAutoRunAnalysis,
|
||||
setWindowParameters,
|
||||
brushSelectionUpdateHandler,
|
||||
adjustedChartPoints,
|
||||
|
@ -535,3 +557,24 @@ export const DocumentCountChart: FC<DocumentCountChartProps> = (props) => {
|
|||
</>
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Functional component that renders a `DocumentCountChart` with additional properties
|
||||
* managed by the log rate analysis state. It leverages the `useLogRateAnalysisStateContext`
|
||||
* to acquire state variables like `initialAnalysisStart` and functions such as
|
||||
* `setAutoRunAnalysis`. These values are then passed as props to the `DocumentCountChart`.
|
||||
*
|
||||
* @param props - The properties passed to the DocumentCountChart component.
|
||||
* @returns The DocumentCountChart component enhanced with automatic analysis start capabilities.
|
||||
*/
|
||||
export const DocumentCountChartWithAutoAnalysisStart: FC<DocumentCountChartProps> = (props) => {
|
||||
const { initialAnalysisStart, setAutoRunAnalysis } = useLogRateAnalysisStateContext();
|
||||
|
||||
return (
|
||||
<DocumentCountChart
|
||||
{...props}
|
||||
autoAnalysisStart={initialAnalysisStart}
|
||||
setAutoRunAnalysis={setAutoRunAnalysis}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
|
|
@ -5,7 +5,10 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
export { DocumentCountChart } from './document_count_chart';
|
||||
export {
|
||||
DocumentCountChart,
|
||||
DocumentCountChartWithAutoAnalysisStart,
|
||||
} from './document_count_chart';
|
||||
export type {
|
||||
BrushSelectionUpdateHandler,
|
||||
BrushSettings,
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
export {
|
||||
useLogRateAnalysisStateContext,
|
||||
LogRateAnalysisStateProvider,
|
||||
} from './log_rate_analysis_state_provider';
|
||||
export type { GroupTableItem, GroupTableItemGroup, TableItemAction } from './types';
|
|
@ -16,13 +16,19 @@ import React, {
|
|||
} from 'react';
|
||||
|
||||
import type { SignificantItem } from '@kbn/ml-agg-utils';
|
||||
import type { WindowParameters } from '@kbn/aiops-log-rate-analysis';
|
||||
|
||||
import type { GroupTableItem } from './types';
|
||||
|
||||
type InitialAnalysisStart = number | WindowParameters | undefined;
|
||||
type SignificantItemOrNull = SignificantItem | null;
|
||||
type GroupOrNull = GroupTableItem | null;
|
||||
|
||||
interface LogRateAnalysisResultsTableRow {
|
||||
interface LogRateAnalysisState {
|
||||
autoRunAnalysis: boolean;
|
||||
setAutoRunAnalysis: Dispatch<SetStateAction<boolean>>;
|
||||
initialAnalysisStart: InitialAnalysisStart;
|
||||
setInitialAnalysisStart: Dispatch<SetStateAction<InitialAnalysisStart>>;
|
||||
pinnedSignificantItem: SignificantItemOrNull;
|
||||
setPinnedSignificantItem: Dispatch<SetStateAction<SignificantItemOrNull>>;
|
||||
pinnedGroup: GroupOrNull;
|
||||
|
@ -36,12 +42,38 @@ interface LogRateAnalysisResultsTableRow {
|
|||
clearAllRowState: () => void;
|
||||
}
|
||||
|
||||
export const logRateAnalysisResultsTableRowContext = createContext<
|
||||
LogRateAnalysisResultsTableRow | undefined
|
||||
>(undefined);
|
||||
const LogRateAnalysisStateContext = createContext<LogRateAnalysisState | undefined>(undefined);
|
||||
|
||||
export const LogRateAnalysisResultsTableRowStateProvider: FC = ({ children }) => {
|
||||
// State that will be shared with all components
|
||||
/**
|
||||
* Props for LogRateAnalysisStateProvider.
|
||||
*/
|
||||
interface LogRateAnalysisStateProviderProps {
|
||||
/** The parameters to be used to trigger an analysis. */
|
||||
initialAnalysisStart?: InitialAnalysisStart;
|
||||
}
|
||||
|
||||
/**
|
||||
* Context provider component that manages and provides global state for Log Rate Analysis.
|
||||
* This provider handles several pieces of state important for controlling and displaying
|
||||
* log rate analysis data, such as the control of automatic analysis runs, and the management
|
||||
* of both pinned and selected significant items and groups.
|
||||
*
|
||||
* The state includes mechanisms for setting initial analysis parameters, toggling analysis,
|
||||
* and managing the current selection and pinned state of significant items and groups.
|
||||
*
|
||||
* @param props - Props object containing initial settings for the analysis,
|
||||
* including children components to be wrapped by the Provider.
|
||||
* @returns A context provider wrapping children with access to log rate analysis state.
|
||||
*/
|
||||
export const LogRateAnalysisStateProvider: FC<LogRateAnalysisStateProviderProps> = (props) => {
|
||||
const { children, initialAnalysisStart: incomingInitialAnalysisStart } = props;
|
||||
|
||||
const [autoRunAnalysis, setAutoRunAnalysis] = useState(true);
|
||||
const [initialAnalysisStart, setInitialAnalysisStart] = useState<
|
||||
number | WindowParameters | undefined
|
||||
>(incomingInitialAnalysisStart);
|
||||
|
||||
// Row state that will be shared with all components
|
||||
const [pinnedSignificantItem, setPinnedSignificantItem] = useState<SignificantItemOrNull>(null);
|
||||
const [pinnedGroup, setPinnedGroup] = useState<GroupOrNull>(null);
|
||||
const [selectedSignificantItem, setSelectedSignificantItem] =
|
||||
|
@ -66,8 +98,12 @@ export const LogRateAnalysisResultsTableRowStateProvider: FC = ({ children }) =>
|
|||
}
|
||||
}, [selectedGroup, pinnedGroup]);
|
||||
|
||||
const contextValue: LogRateAnalysisResultsTableRow = useMemo(
|
||||
const contextValue: LogRateAnalysisState = useMemo(
|
||||
() => ({
|
||||
autoRunAnalysis,
|
||||
setAutoRunAnalysis,
|
||||
initialAnalysisStart,
|
||||
setInitialAnalysisStart,
|
||||
pinnedSignificantItem,
|
||||
setPinnedSignificantItem,
|
||||
pinnedGroup,
|
||||
|
@ -86,6 +122,10 @@ export const LogRateAnalysisResultsTableRowStateProvider: FC = ({ children }) =>
|
|||
},
|
||||
}),
|
||||
[
|
||||
autoRunAnalysis,
|
||||
setAutoRunAnalysis,
|
||||
initialAnalysisStart,
|
||||
setInitialAnalysisStart,
|
||||
pinnedSignificantItem,
|
||||
setPinnedSignificantItem,
|
||||
pinnedGroup,
|
||||
|
@ -101,19 +141,26 @@ export const LogRateAnalysisResultsTableRowStateProvider: FC = ({ children }) =>
|
|||
|
||||
return (
|
||||
// Provider managing the state
|
||||
<logRateAnalysisResultsTableRowContext.Provider value={contextValue}>
|
||||
<LogRateAnalysisStateContext.Provider value={contextValue}>
|
||||
{children}
|
||||
</logRateAnalysisResultsTableRowContext.Provider>
|
||||
</LogRateAnalysisStateContext.Provider>
|
||||
);
|
||||
};
|
||||
|
||||
export const useLogRateAnalysisResultsTableRowContext = () => {
|
||||
const logRateAnalysisResultsTableRow = useContext(logRateAnalysisResultsTableRowContext);
|
||||
/**
|
||||
* Custom hook for accessing the state of log rate analysis from the LogRateAnalysisStateContext.
|
||||
* This hook must be used within a component that is a descendant of the LogRateAnalysisStateContext provider.
|
||||
*
|
||||
* @returns The current state of the log rate analysis.
|
||||
* @throws Throws an error if the hook is used outside of its Provider context.
|
||||
*/
|
||||
export const useLogRateAnalysisStateContext = () => {
|
||||
const logRateAnalysisState = useContext(LogRateAnalysisStateContext);
|
||||
|
||||
// If `undefined`, throw an error.
|
||||
if (logRateAnalysisResultsTableRow === undefined) {
|
||||
throw new Error('useLogRateAnalysisResultsTableRowContext was used outside of its Provider');
|
||||
if (logRateAnalysisState === undefined) {
|
||||
throw new Error('useLogRateAnalysisStateContext was used outside of its Provider');
|
||||
}
|
||||
|
||||
return logRateAnalysisResultsTableRow;
|
||||
return logRateAnalysisState;
|
||||
};
|
|
@ -9,20 +9,36 @@ import type { EuiTableActionsColumnType } from '@elastic/eui';
|
|||
|
||||
import type { SignificantItem, SignificantItemGroupItem } from '@kbn/ml-agg-utils';
|
||||
|
||||
/**
|
||||
* Type for defining attributes picked from
|
||||
* SignificantItemGroupItem used in the grouped table.
|
||||
*/
|
||||
export type GroupTableItemGroup = Pick<
|
||||
SignificantItemGroupItem,
|
||||
'key' | 'type' | 'fieldName' | 'fieldValue' | 'docCount' | 'pValue' | 'duplicate'
|
||||
>;
|
||||
|
||||
/**
|
||||
* Represents a single item in the group table.
|
||||
*/
|
||||
export interface GroupTableItem {
|
||||
/** Unique identifier for the group table item. */
|
||||
id: string;
|
||||
/** Document count associated with the item. */
|
||||
docCount: number;
|
||||
/** Statistical p-value indicating the significance of the item, nullable. */
|
||||
pValue: number | null;
|
||||
/** Count of unique items within the group. */
|
||||
uniqueItemsCount: number;
|
||||
/** Array of items within the group, sorted by uniqueness. */
|
||||
groupItemsSortedByUniqueness: GroupTableItemGroup[];
|
||||
/** Histogram data for the significant item. */
|
||||
histogram: SignificantItem['histogram'];
|
||||
}
|
||||
|
||||
/**
|
||||
* Type for action columns in a table that involves SignificantItem or GroupTableItem.
|
||||
*/
|
||||
export type TableItemAction = EuiTableActionsColumnType<
|
||||
SignificantItem | GroupTableItem
|
||||
>['actions'][number];
|
|
@ -27,6 +27,7 @@
|
|||
"@kbn/field-formats-plugin",
|
||||
"@kbn/visualization-utils",
|
||||
"@kbn/aiops-log-rate-analysis",
|
||||
"@kbn/ml-agg-utils",
|
||||
],
|
||||
"exclude": [
|
||||
"target/**/*",
|
||||
|
|
|
@ -33,8 +33,14 @@ export const journey = new Journey({
|
|||
await page.waitForSelector(subj('aiopsNoWindowParametersEmptyPrompt'));
|
||||
})
|
||||
.step('Run AIOps Log Rate Analysis', async ({ page }) => {
|
||||
// Select the chart and click in the area where the spike is located to trigger log rate analysis.
|
||||
// Select the chart and click in the area where the spike is located.
|
||||
const chart = await page.locator(subj('aiopsDocumentCountChart'));
|
||||
await chart.click({ position: { x: 710, y: 50 } });
|
||||
|
||||
// Click the "Run analysis" button.
|
||||
await page.waitForSelector(subj('aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton'));
|
||||
await page.click(subj('aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton'));
|
||||
|
||||
// Wait for the analysis to complete.
|
||||
await page.waitForSelector(subj('aiopsAnalysisComplete'), { timeout: 120000 });
|
||||
});
|
||||
|
|
|
@ -6,8 +6,7 @@
|
|||
*/
|
||||
|
||||
import type { SignificantItem } from '@kbn/ml-agg-utils';
|
||||
|
||||
import type { GroupTableItem } from '../../components/log_rate_analysis_results_table/types';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import { buildExtendedBaseFilterCriteria } from './build_extended_base_filter_criteria';
|
||||
|
||||
|
|
|
@ -14,8 +14,7 @@ import type { Query } from '@kbn/es-query';
|
|||
import { type SignificantItem, SIGNIFICANT_ITEM_TYPE } from '@kbn/ml-agg-utils';
|
||||
import { buildBaseFilterCriteria } from '@kbn/ml-query-utils';
|
||||
import { getCategoryQuery } from '@kbn/aiops-log-pattern-analysis/get_category_query';
|
||||
|
||||
import type { GroupTableItem } from '../../components/log_rate_analysis_results_table/types';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
/*
|
||||
* Contains utility functions for building and processing queries.
|
||||
|
|
|
@ -14,7 +14,10 @@ import type {
|
|||
} from '@elastic/charts/dist/chart_types/xy_chart/utils/specs';
|
||||
|
||||
import type { LogRateHistogramItem, WindowParameters } from '@kbn/aiops-log-rate-analysis';
|
||||
import { DocumentCountChart, type BrushSelectionUpdateHandler } from '@kbn/aiops-components';
|
||||
import {
|
||||
DocumentCountChartWithAutoAnalysisStart,
|
||||
type BrushSelectionUpdateHandler,
|
||||
} from '@kbn/aiops-components';
|
||||
|
||||
import { useAiopsAppContext } from '../../../hooks/use_aiops_app_context';
|
||||
import type { DocumentCountStats } from '../../../get_document_stats';
|
||||
|
@ -29,13 +32,11 @@ export interface DocumentCountContentProps {
|
|||
isBrushCleared: boolean;
|
||||
totalCount: number;
|
||||
sampleProbability: number;
|
||||
initialAnalysisStart?: number | WindowParameters;
|
||||
/** Optional color override for the default bar color for charts */
|
||||
barColorOverride?: string;
|
||||
/** Optional color override for the highlighted bar color for charts */
|
||||
barHighlightColorOverride?: string;
|
||||
windowParameters?: WindowParameters;
|
||||
incomingInitialAnalysisStart?: number | WindowParameters;
|
||||
baselineLabel?: string;
|
||||
deviationLabel?: string;
|
||||
barStyleAccessor?: BarStyleAccessor;
|
||||
|
@ -51,11 +52,9 @@ export const DocumentCountContent: FC<DocumentCountContentProps> = ({
|
|||
isBrushCleared,
|
||||
totalCount,
|
||||
sampleProbability,
|
||||
initialAnalysisStart,
|
||||
barColorOverride,
|
||||
barHighlightColorOverride,
|
||||
windowParameters,
|
||||
incomingInitialAnalysisStart,
|
||||
...docCountChartProps
|
||||
}) => {
|
||||
const { data, uiSettings, fieldFormats, charts } = useAiopsAppContext();
|
||||
|
@ -100,7 +99,7 @@ export const DocumentCountContent: FC<DocumentCountContentProps> = ({
|
|||
</EuiFlexItem>
|
||||
{documentCountStats.interval !== undefined && (
|
||||
<EuiFlexItem>
|
||||
<DocumentCountChart
|
||||
<DocumentCountChartWithAutoAnalysisStart
|
||||
dependencies={{ data, uiSettings, fieldFormats, charts }}
|
||||
brushSelectionUpdateHandler={brushSelectionUpdateHandler}
|
||||
chartPoints={chartPoints}
|
||||
|
@ -110,7 +109,6 @@ export const DocumentCountContent: FC<DocumentCountContentProps> = ({
|
|||
interval={documentCountStats.interval}
|
||||
chartPointsSplitLabel={documentCountStatsSplitLabel}
|
||||
isBrushCleared={isBrushCleared}
|
||||
autoAnalysisStart={initialAnalysisStart}
|
||||
barColorOverride={barColorOverride}
|
||||
barHighlightColorOverride={barHighlightColorOverride}
|
||||
changePoint={documentCountStats.changePoint}
|
||||
|
|
|
@ -17,13 +17,12 @@ import { Storage } from '@kbn/kibana-utils-plugin/public';
|
|||
import { DatePickerContextProvider, type DatePickerDependencies } from '@kbn/ml-date-picker';
|
||||
import { UI_SETTINGS } from '@kbn/data-plugin/common';
|
||||
|
||||
import { LogRateAnalysisStateProvider } from '@kbn/aiops-components';
|
||||
import type { AiopsAppDependencies } from '../../hooks/use_aiops_app_context';
|
||||
import { AiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
import { DataSourceContext } from '../../hooks/use_data_source';
|
||||
import { AIOPS_STORAGE_KEYS } from '../../types/storage';
|
||||
|
||||
import { LogRateAnalysisResultsTableRowStateProvider } from '../log_rate_analysis_results_table/log_rate_analysis_results_table_row_provider';
|
||||
|
||||
import { LogRateAnalysisPage } from './log_rate_analysis_page';
|
||||
import { timeSeriesDataViewWarning } from '../../application/utils/time_series_dataview_check';
|
||||
|
||||
|
@ -70,13 +69,13 @@ export const LogRateAnalysisAppState: FC<LogRateAnalysisAppStateProps> = ({
|
|||
<AiopsAppContext.Provider value={appDependencies}>
|
||||
<UrlStateProvider>
|
||||
<DataSourceContext.Provider value={{ dataView, savedSearch }}>
|
||||
<LogRateAnalysisResultsTableRowStateProvider>
|
||||
<LogRateAnalysisStateProvider>
|
||||
<StorageContextProvider storage={localStorage} storageKeys={AIOPS_STORAGE_KEYS}>
|
||||
<DatePickerContextProvider {...datePickerDeps}>
|
||||
<LogRateAnalysisPage stickyHistogram={stickyHistogram} />
|
||||
</DatePickerContextProvider>
|
||||
</StorageContextProvider>
|
||||
</LogRateAnalysisResultsTableRowStateProvider>
|
||||
</LogRateAnalysisStateProvider>
|
||||
</DataSourceContext.Provider>
|
||||
</UrlStateProvider>
|
||||
</AiopsAppContext.Provider>
|
||||
|
|
|
@ -26,6 +26,7 @@ import {
|
|||
type WindowParameters,
|
||||
} from '@kbn/aiops-log-rate-analysis';
|
||||
import type { SignificantItem } from '@kbn/ml-agg-utils';
|
||||
import { useLogRateAnalysisStateContext, type GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import { useData } from '../../../hooks/use_data';
|
||||
|
||||
|
@ -34,8 +35,6 @@ import {
|
|||
LogRateAnalysisResults,
|
||||
type LogRateAnalysisResultsData,
|
||||
} from '../log_rate_analysis_results';
|
||||
import type { GroupTableItem } from '../../log_rate_analysis_results_table/types';
|
||||
import { useLogRateAnalysisResultsTableRowContext } from '../../log_rate_analysis_results_table/log_rate_analysis_results_table_row_provider';
|
||||
|
||||
const DEFAULT_SEARCH_QUERY: estypes.QueryDslQueryContainer = { match_all: {} };
|
||||
const DEFAULT_SEARCH_BAR_QUERY: estypes.QueryDslQueryContainer = {
|
||||
|
@ -66,8 +65,6 @@ export function getDocumentCountStatsSplitLabel(
|
|||
export interface LogRateAnalysisContentProps {
|
||||
/** The data view to analyze. */
|
||||
dataView: DataView;
|
||||
/** Timestamp for the start of the range for initial analysis */
|
||||
initialAnalysisStart?: number | WindowParameters;
|
||||
timeRange?: { min: Moment; max: Moment };
|
||||
/** Elasticsearch query to pass to analysis endpoint */
|
||||
esSearchQuery?: estypes.QueryDslQueryContainer;
|
||||
|
@ -87,7 +84,6 @@ export interface LogRateAnalysisContentProps {
|
|||
|
||||
export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
||||
dataView,
|
||||
initialAnalysisStart: incomingInitialAnalysisStart,
|
||||
timeRange,
|
||||
esSearchQuery = DEFAULT_SEARCH_QUERY,
|
||||
stickyHistogram,
|
||||
|
@ -98,9 +94,6 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
embeddingOrigin,
|
||||
}) => {
|
||||
const [windowParameters, setWindowParameters] = useState<WindowParameters | undefined>();
|
||||
const [initialAnalysisStart, setInitialAnalysisStart] = useState<
|
||||
number | WindowParameters | undefined
|
||||
>(incomingInitialAnalysisStart);
|
||||
const [isBrushCleared, setIsBrushCleared] = useState(true);
|
||||
const [logRateAnalysisType, setLogRateAnalysisType] = useState<LogRateAnalysisType>(
|
||||
LOG_RATE_ANALYSIS_TYPE.SPIKE
|
||||
|
@ -140,13 +133,16 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
);
|
||||
|
||||
const {
|
||||
autoRunAnalysis,
|
||||
currentSelectedSignificantItem,
|
||||
currentSelectedGroup,
|
||||
setAutoRunAnalysis,
|
||||
setInitialAnalysisStart,
|
||||
setPinnedSignificantItem,
|
||||
setPinnedGroup,
|
||||
setSelectedSignificantItem,
|
||||
setSelectedGroup,
|
||||
} = useLogRateAnalysisResultsTableRowContext();
|
||||
} = useLogRateAnalysisStateContext();
|
||||
|
||||
const { documentStats, earliest, latest } = useData(
|
||||
dataView,
|
||||
|
@ -206,7 +202,11 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
}
|
||||
: undefined;
|
||||
|
||||
const triggerAnalysis = useCallback(() => {
|
||||
const triggerAnalysisForManualSelection = useCallback(() => {
|
||||
setAutoRunAnalysis(true);
|
||||
}, [setAutoRunAnalysis]);
|
||||
|
||||
const triggerAnalysisForChangePoint = useCallback(() => {
|
||||
if (documentCountStats) {
|
||||
const { interval, timeRangeEarliest, timeRangeLatest, changePoint } = documentCountStats;
|
||||
|
||||
|
@ -222,14 +222,37 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
const snapTimestamps = getSnappedTimestamps(timeRangeEarliest, timeRangeLatest, interval);
|
||||
const wpSnap = getSnappedWindowParameters(wp, snapTimestamps);
|
||||
|
||||
triggerAnalysisForManualSelection();
|
||||
setInitialAnalysisStart(wpSnap);
|
||||
}
|
||||
}
|
||||
}, [documentCountStats]);
|
||||
}, [documentCountStats, setInitialAnalysisStart, triggerAnalysisForManualSelection]);
|
||||
|
||||
const showDocumentCountContent = documentCountStats !== undefined;
|
||||
|
||||
const showLogRateAnalysisResults =
|
||||
autoRunAnalysis &&
|
||||
earliest !== undefined &&
|
||||
latest !== undefined &&
|
||||
windowParameters !== undefined;
|
||||
|
||||
const showNoAutoRunEmptyPrompt =
|
||||
!autoRunAnalysis &&
|
||||
earliest !== undefined &&
|
||||
latest !== undefined &&
|
||||
windowParameters !== undefined;
|
||||
|
||||
const showSpikeDetectedEmptyPrompt =
|
||||
windowParameters === undefined && documentCountStats?.changePoint;
|
||||
|
||||
const showDefaultEmptyPrompt =
|
||||
windowParameters === undefined && documentCountStats?.changePoint === undefined;
|
||||
|
||||
const changePointType = documentCountStats?.changePoint?.type;
|
||||
|
||||
return (
|
||||
<EuiPanel hasBorder={false} hasShadow={false}>
|
||||
{documentCountStats !== undefined && (
|
||||
{showDocumentCountContent && (
|
||||
<DocumentCountContent
|
||||
brushSelectionUpdateHandler={brushSelectionUpdate}
|
||||
documentCountStats={documentCountStats}
|
||||
|
@ -241,14 +264,13 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
isBrushCleared={isBrushCleared}
|
||||
totalCount={totalCount}
|
||||
sampleProbability={sampleProbability}
|
||||
initialAnalysisStart={initialAnalysisStart}
|
||||
barColorOverride={barColorOverride}
|
||||
barHighlightColorOverride={barHighlightColorOverride}
|
||||
barStyleAccessor={barStyleAccessor}
|
||||
/>
|
||||
)}
|
||||
<EuiHorizontalRule />
|
||||
{earliest !== undefined && latest !== undefined && windowParameters !== undefined && (
|
||||
{showLogRateAnalysisResults && (
|
||||
<LogRateAnalysisResults
|
||||
dataView={dataView}
|
||||
analysisType={logRateAnalysisType}
|
||||
|
@ -266,7 +288,47 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
embeddingOrigin={embeddingOrigin}
|
||||
/>
|
||||
)}
|
||||
{windowParameters === undefined && documentCountStats?.changePoint && (
|
||||
{showNoAutoRunEmptyPrompt && (
|
||||
<EuiEmptyPrompt
|
||||
color="subdued"
|
||||
hasShadow={false}
|
||||
hasBorder={false}
|
||||
css={{ minWidth: '100%' }}
|
||||
title={undefined}
|
||||
titleSize="xs"
|
||||
body={
|
||||
<>
|
||||
<p>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.noAutoRunPromptBody"
|
||||
defaultMessage="Next you can fine tune the time ranges for baseline and deviation by dragging the handles of the brushes. Once you're ready, click the button 'Run analysis' below."
|
||||
/>
|
||||
</p>
|
||||
<EuiButton
|
||||
data-test-subj="aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton"
|
||||
onClick={triggerAnalysisForManualSelection}
|
||||
>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.noAutoRunPromptRunAnalysisButton"
|
||||
defaultMessage="Run analysis"
|
||||
/>
|
||||
</EuiButton>{' '}
|
||||
<EuiButton
|
||||
data-test-subj="aiopsClearSelectionBadge"
|
||||
onClick={() => clearSelection()}
|
||||
color="text"
|
||||
>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.clearSelectionLabel"
|
||||
defaultMessage="Clear selection"
|
||||
/>
|
||||
</EuiButton>
|
||||
</>
|
||||
}
|
||||
data-test-subj="aiopsChangePointDetectedPrompt"
|
||||
/>
|
||||
)}
|
||||
{showSpikeDetectedEmptyPrompt && (
|
||||
<EuiEmptyPrompt
|
||||
color="subdued"
|
||||
hasShadow={false}
|
||||
|
@ -274,20 +336,20 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
css={{ minWidth: '100%' }}
|
||||
title={
|
||||
<h2>
|
||||
{documentCountStats?.changePoint.type === LOG_RATE_ANALYSIS_TYPE.SPIKE && (
|
||||
{changePointType === LOG_RATE_ANALYSIS_TYPE.SPIKE && (
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.changePointSpikePromptTitle"
|
||||
defaultMessage="Log rate spike detected"
|
||||
/>
|
||||
)}
|
||||
{documentCountStats?.changePoint.type === LOG_RATE_ANALYSIS_TYPE.DIP && (
|
||||
{changePointType === LOG_RATE_ANALYSIS_TYPE.DIP && (
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.changePointDipPromptTitle"
|
||||
defaultMessage="Log rate dip detected"
|
||||
/>
|
||||
)}
|
||||
{documentCountStats?.changePoint.type !== LOG_RATE_ANALYSIS_TYPE.SPIKE &&
|
||||
documentCountStats?.changePoint.type !== LOG_RATE_ANALYSIS_TYPE.DIP && (
|
||||
{changePointType !== LOG_RATE_ANALYSIS_TYPE.SPIKE &&
|
||||
changePointType !== LOG_RATE_ANALYSIS_TYPE.DIP && (
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.changePointOtherPromptTitle"
|
||||
defaultMessage="Log rate change point detected"
|
||||
|
@ -301,12 +363,12 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
<p>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.changePointPromptBody"
|
||||
defaultMessage="The log rate analysis feature identifies statistically significant field/value combinations that contribute to a log rate spike or dip."
|
||||
defaultMessage="The log rate analysis feature identifies statistically significant field/value combinations that contribute to a log rate spike or dip. To analyse the area highlighted in the chart, click the button below. For custom analysis of other areas, start by clicking on any of the non-highlighted bars in the histogram chart."
|
||||
/>
|
||||
</p>
|
||||
<EuiButton
|
||||
data-test-subj="aiopsLogRateAnalysisContentRunAnalysisButton"
|
||||
onClick={triggerAnalysis}
|
||||
onClick={triggerAnalysisForChangePoint}
|
||||
>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.changePointPromptRunAnalysisButton"
|
||||
|
@ -318,7 +380,7 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
data-test-subj="aiopsChangePointDetectedPrompt"
|
||||
/>
|
||||
)}
|
||||
{windowParameters === undefined && documentCountStats?.changePoint === undefined && (
|
||||
{showDefaultEmptyPrompt && (
|
||||
<EuiEmptyPrompt
|
||||
color="subdued"
|
||||
hasShadow={false}
|
||||
|
@ -328,7 +390,7 @@ export const LogRateAnalysisContent: FC<LogRateAnalysisContentProps> = ({
|
|||
<h2>
|
||||
<FormattedMessage
|
||||
id="xpack.aiops.logRateAnalysis.page.emptyPromptTitle"
|
||||
defaultMessage="Click a spike or dip in the histogram chart to start the analysis."
|
||||
defaultMessage="Start by clicking a spike or dip in the histogram chart."
|
||||
/>
|
||||
</h2>
|
||||
}
|
||||
|
|
|
@ -18,13 +18,13 @@ import { UrlStateProvider } from '@kbn/ml-url-state';
|
|||
import { Storage } from '@kbn/kibana-utils-plugin/public';
|
||||
import { DatePickerContextProvider } from '@kbn/ml-date-picker';
|
||||
import { UI_SETTINGS } from '@kbn/data-plugin/common';
|
||||
import { LogRateAnalysisStateProvider } from '@kbn/aiops-components';
|
||||
|
||||
import { timeSeriesDataViewWarning } from '../../../application/utils/time_series_dataview_check';
|
||||
import { AiopsAppContext, type AiopsAppDependencies } from '../../../hooks/use_aiops_app_context';
|
||||
import { DataSourceContext } from '../../../hooks/use_data_source';
|
||||
import { AIOPS_STORAGE_KEYS } from '../../../types/storage';
|
||||
|
||||
import { LogRateAnalysisResultsTableRowStateProvider } from '../../log_rate_analysis_results_table/log_rate_analysis_results_table_row_provider';
|
||||
import { LogRateAnalysisContent } from './log_rate_analysis_content';
|
||||
import type { LogRateAnalysisResultsData } from '../log_rate_analysis_results';
|
||||
|
||||
|
@ -92,12 +92,11 @@ export const LogRateAnalysisContentWrapper: FC<LogRateAnalysisContentWrapperProp
|
|||
<AiopsAppContext.Provider value={appDependencies}>
|
||||
<UrlStateProvider>
|
||||
<DataSourceContext.Provider value={{ dataView, savedSearch: null }}>
|
||||
<LogRateAnalysisResultsTableRowStateProvider>
|
||||
<LogRateAnalysisStateProvider initialAnalysisStart={initialAnalysisStart}>
|
||||
<StorageContextProvider storage={localStorage} storageKeys={AIOPS_STORAGE_KEYS}>
|
||||
<DatePickerContextProvider {...datePickerDeps}>
|
||||
<LogRateAnalysisContent
|
||||
dataView={dataView}
|
||||
initialAnalysisStart={initialAnalysisStart}
|
||||
timeRange={timeRange}
|
||||
esSearchQuery={esSearchQuery}
|
||||
stickyHistogram={stickyHistogram}
|
||||
|
@ -108,7 +107,7 @@ export const LogRateAnalysisContentWrapper: FC<LogRateAnalysisContentWrapperProp
|
|||
/>
|
||||
</DatePickerContextProvider>
|
||||
</StorageContextProvider>
|
||||
</LogRateAnalysisResultsTableRowStateProvider>
|
||||
</LogRateAnalysisStateProvider>
|
||||
</DataSourceContext.Provider>
|
||||
</UrlStateProvider>
|
||||
</AiopsAppContext.Provider>
|
||||
|
|
|
@ -18,6 +18,7 @@ import { useUrlState, usePageUrlState } from '@kbn/ml-url-state';
|
|||
import type { SearchQueryLanguage } from '@kbn/ml-query-utils';
|
||||
import type { WindowParameters } from '@kbn/aiops-log-rate-analysis';
|
||||
import { AIOPS_TELEMETRY_ID } from '@kbn/aiops-common/constants';
|
||||
import { useLogRateAnalysisStateContext } from '@kbn/aiops-components';
|
||||
|
||||
import { useDataSource } from '../../hooks/use_data_source';
|
||||
import { useAiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
|
@ -31,7 +32,6 @@ import {
|
|||
} from '../../application/url_state/log_rate_analysis';
|
||||
|
||||
import { SearchPanel } from '../search_panel';
|
||||
import { useLogRateAnalysisResultsTableRowContext } from '../log_rate_analysis_results_table/log_rate_analysis_results_table_row_provider';
|
||||
import { PageHeader } from '../page_header';
|
||||
|
||||
import { LogRateAnalysisContent } from './log_rate_analysis_content/log_rate_analysis_content';
|
||||
|
@ -43,8 +43,8 @@ export const LogRateAnalysisPage: FC<Props> = ({ stickyHistogram }) => {
|
|||
const { data: dataService } = useAiopsAppContext();
|
||||
const { dataView, savedSearch } = useDataSource();
|
||||
|
||||
const { currentSelectedSignificantItem, currentSelectedGroup } =
|
||||
useLogRateAnalysisResultsTableRowContext();
|
||||
const { currentSelectedSignificantItem, currentSelectedGroup, setInitialAnalysisStart } =
|
||||
useLogRateAnalysisStateContext();
|
||||
|
||||
const [stateFromUrl, setUrlState] = usePageUrlState<LogRateAnalysisPageUrlState>(
|
||||
'logRateAnalysis',
|
||||
|
@ -142,6 +142,14 @@ export const LogRateAnalysisPage: FC<Props> = ({ stickyHistogram }) => {
|
|||
});
|
||||
}, [dataService, searchQueryLanguage, searchString]);
|
||||
|
||||
useEffect(
|
||||
() => {
|
||||
setInitialAnalysisStart(appStateToWindowParameters(stateFromUrl.wp));
|
||||
},
|
||||
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||
[]
|
||||
);
|
||||
|
||||
const onWindowParametersHandler = (wp?: WindowParameters, replace = false) => {
|
||||
if (!isEqual(windowParametersToAppState(wp), stateFromUrl.wp)) {
|
||||
setUrlState(
|
||||
|
@ -169,7 +177,6 @@ export const LogRateAnalysisPage: FC<Props> = ({ stickyHistogram }) => {
|
|||
/>
|
||||
</EuiFlexItem>
|
||||
<LogRateAnalysisContent
|
||||
initialAnalysisStart={appStateToWindowParameters(stateFromUrl.wp)}
|
||||
dataView={dataView}
|
||||
embeddingOrigin={AIOPS_TELEMETRY_ID.AIOPS_DEFAULT_SOURCE}
|
||||
esSearchQuery={searchQuery}
|
||||
|
|
|
@ -38,6 +38,7 @@ import { AIOPS_TELEMETRY_ID } from '@kbn/aiops-common/constants';
|
|||
import { initialState, streamReducer } from '@kbn/aiops-log-rate-analysis/api/stream_reducer';
|
||||
import type { AiopsLogRateAnalysisSchema } from '@kbn/aiops-log-rate-analysis/api/schema';
|
||||
import type { AiopsLogRateAnalysisSchemaSignificantItem } from '@kbn/aiops-log-rate-analysis/api/schema_v2';
|
||||
import { useLogRateAnalysisStateContext } from '@kbn/aiops-components';
|
||||
|
||||
import { useAiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
import {
|
||||
|
@ -45,7 +46,6 @@ import {
|
|||
LogRateAnalysisResultsTable,
|
||||
LogRateAnalysisResultsGroupsTable,
|
||||
} from '../log_rate_analysis_results_table';
|
||||
import { useLogRateAnalysisResultsTableRowContext } from '../log_rate_analysis_results_table/log_rate_analysis_results_table_row_provider';
|
||||
|
||||
import { FieldFilterPopover } from './field_filter_popover';
|
||||
import { LogRateAnalysisTypeCallOut } from './log_rate_analysis_type_callout';
|
||||
|
@ -144,7 +144,7 @@ export const LogRateAnalysisResults: FC<LogRateAnalysisResultsProps> = ({
|
|||
// to be able to track it across rerenders.
|
||||
const analysisStartTime = useRef<number | undefined>(window.performance.now());
|
||||
|
||||
const { clearAllRowState } = useLogRateAnalysisResultsTableRowContext();
|
||||
const { clearAllRowState } = useLogRateAnalysisStateContext();
|
||||
|
||||
const [currentAnalysisType, setCurrentAnalysisType] = useState<LogRateAnalysisType | undefined>();
|
||||
const [currentAnalysisWindowParameters, setCurrentAnalysisWindowParameters] = useState<
|
||||
|
|
|
@ -8,8 +8,7 @@
|
|||
import { sortBy } from 'lodash';
|
||||
|
||||
import type { SignificantItemGroup } from '@kbn/ml-agg-utils';
|
||||
|
||||
import type { GroupTableItem, GroupTableItemGroup } from './types';
|
||||
import type { GroupTableItem, GroupTableItemGroup } from '@kbn/aiops-components';
|
||||
|
||||
export function getGroupTableItems(
|
||||
significantItemsGroups: SignificantItemGroup[]
|
||||
|
|
|
@ -7,8 +7,7 @@
|
|||
|
||||
import { escapeKuery, escapeQuotes } from '@kbn/es-query';
|
||||
import { isSignificantItem, type SignificantItem } from '@kbn/ml-agg-utils';
|
||||
|
||||
import type { GroupTableItem } from './types';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
export const getTableItemAsKQL = (tableItem: GroupTableItem | SignificantItem) => {
|
||||
if (isSignificantItem(tableItem)) {
|
||||
|
|
|
@ -32,13 +32,13 @@ import type { TimeRange as TimeRangeMs } from '@kbn/ml-date-picker';
|
|||
|
||||
import { getCategoryQuery } from '@kbn/aiops-log-pattern-analysis/get_category_query';
|
||||
|
||||
import { useLogRateAnalysisStateContext } from '@kbn/aiops-components';
|
||||
import { useEuiTheme } from '../../hooks/use_eui_theme';
|
||||
|
||||
import { MiniHistogram } from '../mini_histogram';
|
||||
import { useAiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
|
||||
import { getFailedTransactionsCorrelationImpactLabel } from './get_failed_transactions_correlation_impact_label';
|
||||
import { useLogRateAnalysisResultsTableRowContext } from './log_rate_analysis_results_table_row_provider';
|
||||
import { FieldStatsPopover } from '../field_stats_popover';
|
||||
import { useCopyToClipboardAction } from './use_copy_to_clipboard_action';
|
||||
import { useViewInDiscoverAction } from './use_view_in_discover_action';
|
||||
|
@ -93,7 +93,7 @@ export const LogRateAnalysisResultsTable: FC<LogRateAnalysisResultsTableProps> =
|
|||
selectedSignificantItem,
|
||||
setPinnedSignificantItem,
|
||||
setSelectedSignificantItem,
|
||||
} = useLogRateAnalysisResultsTableRowContext();
|
||||
} = useLogRateAnalysisStateContext();
|
||||
|
||||
const [pageIndex, setPageIndex] = useState(0);
|
||||
const [pageSize, setPageSize] = useState(10);
|
||||
|
|
|
@ -32,13 +32,12 @@ import type { SignificantItem } from '@kbn/ml-agg-utils';
|
|||
import type { TimeRange as TimeRangeMs } from '@kbn/ml-date-picker';
|
||||
import type { DataView } from '@kbn/data-views-plugin/public';
|
||||
import { stringHash } from '@kbn/ml-string-hash';
|
||||
import { useLogRateAnalysisStateContext, type GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import { MiniHistogram } from '../mini_histogram';
|
||||
|
||||
import { getFailedTransactionsCorrelationImpactLabel } from './get_failed_transactions_correlation_impact_label';
|
||||
import { LogRateAnalysisResultsTable } from './log_rate_analysis_results_table';
|
||||
import { useLogRateAnalysisResultsTableRowContext } from './log_rate_analysis_results_table_row_provider';
|
||||
import type { GroupTableItem } from './types';
|
||||
import { useCopyToClipboardAction } from './use_copy_to_clipboard_action';
|
||||
import { useViewInDiscoverAction } from './use_view_in_discover_action';
|
||||
import { useViewInLogPatternAnalysisAction } from './use_view_in_log_pattern_analysis_action';
|
||||
|
@ -97,7 +96,7 @@ export const LogRateAnalysisResultsGroupsTable: FC<LogRateAnalysisResultsTablePr
|
|||
const primaryBackgroundColor = useEuiBackgroundColor('primary');
|
||||
|
||||
const { pinnedGroup, selectedGroup, setPinnedGroup, setSelectedGroup } =
|
||||
useLogRateAnalysisResultsTableRowContext();
|
||||
useLogRateAnalysisStateContext();
|
||||
const dataViewId = dataView.id;
|
||||
|
||||
const toggleDetails = (item: GroupTableItem) => {
|
||||
|
|
|
@ -14,10 +14,10 @@ import type { SignificantItem } from '@kbn/ml-agg-utils';
|
|||
|
||||
import { finalSignificantItemGroups } from '@kbn/aiops-test-utils/artificial_logs/final_significant_item_groups';
|
||||
import { significantTerms } from '@kbn/aiops-test-utils/artificial_logs/significant_terms';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import { getGroupTableItems } from './get_group_table_items';
|
||||
import { useCopyToClipboardAction } from './use_copy_to_clipboard_action';
|
||||
import type { GroupTableItem } from './types';
|
||||
|
||||
interface Action {
|
||||
render: (tableItem: SignificantItem | GroupTableItem) => ReactElement;
|
||||
|
|
|
@ -11,10 +11,10 @@ import { EuiCopy, EuiToolTip } from '@elastic/eui';
|
|||
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { isSignificantItem, type SignificantItem } from '@kbn/ml-agg-utils';
|
||||
import type { GroupTableItem, TableItemAction } from '@kbn/aiops-components';
|
||||
|
||||
import { TableActionButton } from './table_action_button';
|
||||
import { getTableItemAsKQL } from './get_table_item_as_kql';
|
||||
import type { GroupTableItem, TableItemAction } from './types';
|
||||
|
||||
const copyToClipboardButtonLabel = i18n.translate(
|
||||
'xpack.aiops.logRateAnalysis.resultsTable.linksMenu.copyToClipboardButtonLabel',
|
||||
|
|
|
@ -9,13 +9,13 @@ import React, { useMemo } from 'react';
|
|||
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import type { SignificantItem } from '@kbn/ml-agg-utils';
|
||||
|
||||
import { SEARCH_QUERY_LANGUAGE } from '@kbn/ml-query-utils';
|
||||
import type { GroupTableItem, TableItemAction } from '@kbn/aiops-components';
|
||||
|
||||
import { useAiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
|
||||
import { TableActionButton } from './table_action_button';
|
||||
import { getTableItemAsKQL } from './get_table_item_as_kql';
|
||||
import type { GroupTableItem, TableItemAction } from './types';
|
||||
|
||||
const viewInDiscoverMessage = i18n.translate(
|
||||
'xpack.aiops.logRateAnalysis.resultsTable.linksMenu.viewInDiscover',
|
||||
|
|
|
@ -11,13 +11,13 @@ import type { SerializableRecord } from '@kbn/utility-types';
|
|||
import { fromKueryExpression, toElasticsearchQuery } from '@kbn/es-query';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { isSignificantItem, type SignificantItem, SIGNIFICANT_ITEM_TYPE } from '@kbn/ml-agg-utils';
|
||||
import type { GroupTableItem, TableItemAction } from '@kbn/aiops-components';
|
||||
|
||||
import { SEARCH_QUERY_LANGUAGE } from '@kbn/ml-query-utils';
|
||||
import { useAiopsAppContext } from '../../hooks/use_aiops_app_context';
|
||||
|
||||
import { TableActionButton } from './table_action_button';
|
||||
import { getTableItemAsKQL } from './get_table_item_as_kql';
|
||||
import type { GroupTableItem, TableItemAction } from './types';
|
||||
|
||||
const isLogPattern = (tableItem: SignificantItem | GroupTableItem) =>
|
||||
isSignificantItem(tableItem) && tableItem.type === SIGNIFICANT_ITEM_TYPE.LOG_PATTERN;
|
||||
|
|
|
@ -18,9 +18,9 @@ import { isPopulatedObject } from '@kbn/ml-is-populated-object';
|
|||
import type { SignificantItem } from '@kbn/ml-agg-utils';
|
||||
import type { Query } from '@kbn/es-query';
|
||||
import type { RandomSamplerWrapper } from '@kbn/ml-random-sampler-utils';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import { buildExtendedBaseFilterCriteria } from './application/utils/build_extended_base_filter_criteria';
|
||||
import type { GroupTableItem } from './components/log_rate_analysis_results_table/types';
|
||||
|
||||
export interface DocumentCountStats {
|
||||
interval?: number;
|
||||
|
|
|
@ -18,9 +18,9 @@ import type { Dictionary } from '@kbn/ml-url-state';
|
|||
import { mlTimefilterRefresh$, useTimefilter } from '@kbn/ml-date-picker';
|
||||
import { useTimeBuckets } from '@kbn/ml-time-buckets';
|
||||
import { AIOPS_PLUGIN_ID } from '@kbn/aiops-common/constants';
|
||||
import type { GroupTableItem } from '@kbn/aiops-components';
|
||||
|
||||
import type { DocumentStatsSearchStrategyParams } from '../get_document_stats';
|
||||
import type { GroupTableItem } from '../components/log_rate_analysis_results_table/types';
|
||||
|
||||
import { useAiopsAppContext } from './use_aiops_app_context';
|
||||
|
||||
|
|
|
@ -80,6 +80,12 @@ export default function ({ getPageObjects, getService }: FtrProviderContext) {
|
|||
|
||||
await ml.testExecution.logTestStep('clicks the document count chart to start analysis');
|
||||
await aiops.logRateAnalysisPage.clickDocumentCountChart(testData.chartClickCoordinates);
|
||||
|
||||
if (!testData.autoRun) {
|
||||
await aiops.logRateAnalysisPage.assertNoAutoRunButtonExists();
|
||||
await aiops.logRateAnalysisPage.clickNoAutoRunButton();
|
||||
}
|
||||
|
||||
await aiops.logRateAnalysisPage.assertAnalysisSectionExists();
|
||||
|
||||
if (testData.brushDeviationTargetTimestamp) {
|
||||
|
|
|
@ -34,12 +34,14 @@ interface GetArtificialLogDataViewTestDataOptions {
|
|||
analysisType: LogRateAnalysisType;
|
||||
textField: boolean;
|
||||
zeroDocsFallback: boolean;
|
||||
autoRun: boolean;
|
||||
}
|
||||
|
||||
export const getArtificialLogDataViewTestData = ({
|
||||
analysisType,
|
||||
textField,
|
||||
zeroDocsFallback,
|
||||
autoRun,
|
||||
}: GetArtificialLogDataViewTestDataOptions): TestData => {
|
||||
function getAnalysisGroupsTable() {
|
||||
if (zeroDocsFallback) {
|
||||
|
@ -133,6 +135,7 @@ export const getArtificialLogDataViewTestData = ({
|
|||
return {
|
||||
suiteTitle: getSuiteTitle(),
|
||||
analysisType,
|
||||
autoRun,
|
||||
dataGenerator: getDataGenerator(),
|
||||
isSavedSearch: false,
|
||||
sourceIndexOrSavedSearch: getDataGenerator(),
|
||||
|
|
|
@ -12,6 +12,7 @@ import type { TestData } from '../../types';
|
|||
export const farequoteDataViewTestData: TestData = {
|
||||
suiteTitle: 'farequote with spike',
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
autoRun: false,
|
||||
dataGenerator: 'farequote_with_spike',
|
||||
isSavedSearch: false,
|
||||
sourceIndexOrSavedSearch: 'ft_farequote',
|
||||
|
|
|
@ -12,6 +12,7 @@ import type { TestData } from '../../types';
|
|||
export const farequoteDataViewTestDataWithQuery: TestData = {
|
||||
suiteTitle: 'farequote with spike',
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
autoRun: false,
|
||||
dataGenerator: 'farequote_with_spike',
|
||||
isSavedSearch: false,
|
||||
sourceIndexOrSavedSearch: 'ft_farequote',
|
||||
|
|
|
@ -13,6 +13,7 @@ import type { TestData } from '../../types';
|
|||
export const kibanaLogsDataViewTestData: TestData = {
|
||||
suiteTitle: 'kibana sample data logs',
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
autoRun: true,
|
||||
dataGenerator: 'kibana_sample_data_logs',
|
||||
isSavedSearch: false,
|
||||
sourceIndexOrSavedSearch: 'kibana_sample_data_logstsdb',
|
||||
|
|
|
@ -22,40 +22,48 @@ export const logRateAnalysisTestData: TestData[] = [
|
|||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
textField: false,
|
||||
zeroDocsFallback: false,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
textField: true,
|
||||
zeroDocsFallback: false,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.DIP,
|
||||
textField: false,
|
||||
zeroDocsFallback: false,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.DIP,
|
||||
textField: true,
|
||||
zeroDocsFallback: false,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
textField: true,
|
||||
zeroDocsFallback: true,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.SPIKE,
|
||||
textField: false,
|
||||
zeroDocsFallback: true,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.DIP,
|
||||
textField: true,
|
||||
zeroDocsFallback: true,
|
||||
autoRun: false,
|
||||
}),
|
||||
getArtificialLogDataViewTestData({
|
||||
analysisType: LOG_RATE_ANALYSIS_TYPE.DIP,
|
||||
textField: false,
|
||||
zeroDocsFallback: true,
|
||||
autoRun: false,
|
||||
}),
|
||||
];
|
||||
|
|
|
@ -54,6 +54,7 @@ interface TestDataExpectedWithoutSampleProbability {
|
|||
export interface TestData {
|
||||
suiteTitle: string;
|
||||
analysisType: LogRateAnalysisType;
|
||||
autoRun: boolean;
|
||||
dataGenerator: LogRateAnalysisDataGenerator;
|
||||
isSavedSearch?: boolean;
|
||||
sourceIndexOrSavedSearch: string;
|
||||
|
|
|
@ -133,6 +133,16 @@ export function LogRateAnalysisPageProvider({ getService, getPageObject }: FtrPr
|
|||
await this.assertHistogramBrushesExist();
|
||||
},
|
||||
|
||||
async clickNoAutoRunButton() {
|
||||
await testSubjects.clickWhenNotDisabledWithoutRetry(
|
||||
'aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton'
|
||||
);
|
||||
|
||||
await retry.tryForTime(30 * 1000, async () => {
|
||||
await testSubjects.missingOrFail('aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton');
|
||||
});
|
||||
},
|
||||
|
||||
async clickRerunAnalysisButton(shouldRerun: boolean) {
|
||||
await testSubjects.clickWhenNotDisabledWithoutRetry(
|
||||
`aiopsRerunAnalysisButton${shouldRerun ? ' shouldRerun' : ''}`
|
||||
|
@ -250,6 +260,10 @@ export function LogRateAnalysisPageProvider({ getService, getPageObject }: FtrPr
|
|||
);
|
||||
},
|
||||
|
||||
async assertNoAutoRunButtonExists() {
|
||||
await testSubjects.existOrFail('aiopsLogRateAnalysisNoAutoRunContentRunAnalysisButton');
|
||||
},
|
||||
|
||||
async assertProgressTitle(expectedProgressTitle: string) {
|
||||
await retry.tryForTime(30 * 1000, async () => {
|
||||
await testSubjects.existOrFail('aiopProgressTitle');
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue