[Security Solution][Detections] Immediately refresh exceptions when new list is created after rule creation (#81014)

* ExceptionIdentifiers -> ExceptionListIdentifiers

* Pass refreshRule through to alert context menu

* Fix type errors and rename refreshRule to onRuleChange for consistency
This commit is contained in:
Madison Caldwell 2020-10-20 17:03:47 -04:00 committed by GitHub
parent cdf276cc36
commit 6b6bfe5ef5
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
17 changed files with 48 additions and 18 deletions

View file

@ -23,7 +23,7 @@ export type ReturnExceptionListAndItems = [
* Hook for using to get an ExceptionList and it's ExceptionListItems
*
* @param http Kibana http service
* @param lists array of ExceptionIdentifiers for all lists to fetch
* @param lists array of ExceptionListIdentifiers for all lists to fetch
* @param onError error callback
* @param onSuccess callback when all lists fetched successfully
* @param filterOptions optional - filter by fields or tags

View file

@ -50,7 +50,7 @@ export interface UseExceptionListSuccess {
export interface UseExceptionListProps {
http: HttpStart;
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
onError?: (arg: string[]) => void;
filterOptions: FilterExceptionsOptions[];
pagination?: Pagination;
@ -60,7 +60,7 @@ export interface UseExceptionListProps {
onSuccess?: (arg: UseExceptionListSuccess) => void;
}
export interface ExceptionIdentifiers {
export interface ExceptionListIdentifiers {
id: string;
listId: string;
namespaceType: NamespaceType;
@ -91,7 +91,7 @@ export interface ApiCallMemoProps {
}
export interface ApiCallFindListsItemsMemoProps {
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
filterOptions: FilterExceptionsOptions[];
pagination: Partial<Pagination>;
showDetectionsListsOnly: boolean;

View file

@ -6,14 +6,14 @@
import { NamespaceType } from '../../common/schemas';
import { ExceptionIdentifiers } from './types';
import { ExceptionListIdentifiers } from './types';
export const getIdsAndNamespaces = ({
lists,
showDetection,
showEndpoint,
}: {
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
showDetection: boolean;
showEndpoint: boolean;
}): { ids: string[]; namespaces: NamespaceType[] } =>

View file

@ -30,7 +30,7 @@ export {
} from './exceptions/api';
export {
ExceptionList,
ExceptionIdentifiers,
ExceptionListIdentifiers,
Pagination,
UseExceptionListSuccess,
} from './exceptions/types';

View file

@ -104,6 +104,7 @@ interface Props {
kqlMode: KqlMode;
onChangeItemsPerPage: OnChangeItemsPerPage;
query: Query;
onRuleChange?: () => void;
start: string;
sort: Sort;
toggleColumn: (column: ColumnHeaderOptions) => void;
@ -131,6 +132,7 @@ const EventsViewerComponent: React.FC<Props> = ({
kqlMode,
onChangeItemsPerPage,
query,
onRuleChange,
start,
sort,
toggleColumn,
@ -286,6 +288,7 @@ const EventsViewerComponent: React.FC<Props> = ({
docValueFields={docValueFields}
id={id}
isEventViewer={true}
onRuleChange={onRuleChange}
refetch={refetch}
sort={sort}
toggleColumn={toggleColumn}

View file

@ -42,6 +42,7 @@ export interface OwnProps {
start: string;
headerFilterGroup?: React.ReactNode;
pageFilters?: Filter[];
onRuleChange?: () => void;
utilityBar?: (refetch: inputsModel.Refetch, totalCount: number) => React.ReactNode;
}
@ -64,6 +65,7 @@ const StatefulEventsViewerComponent: React.FC<Props> = ({
kqlMode,
pageFilters,
query,
onRuleChange,
removeColumn,
start,
scopeId,
@ -153,6 +155,7 @@ const StatefulEventsViewerComponent: React.FC<Props> = ({
kqlMode={kqlMode}
onChangeItemsPerPage={onChangeItemsPerPage}
query={query}
onRuleChange={onRuleChange}
start={start}
sort={sort}
toggleColumn={toggleColumn}

View file

@ -18,7 +18,7 @@ import { ExceptionListItemIdentifiers, Filter } from '../types';
import { allExceptionItemsReducer, State, ViewerModalName } from './reducer';
import {
useExceptionList,
ExceptionIdentifiers,
ExceptionListIdentifiers,
ExceptionListTypeEnum,
ExceptionListItemSchema,
UseExceptionListSuccess,
@ -54,7 +54,7 @@ interface ExceptionsViewerProps {
ruleId: string;
ruleName: string;
ruleIndices: string[];
exceptionListsMeta: ExceptionIdentifiers[];
exceptionListsMeta: ExceptionListIdentifiers[];
availableListTypes: ExceptionListTypeEnum[];
commentsAccordionId: string;
onRuleChange?: () => void;

View file

@ -12,7 +12,7 @@ import {
import {
ExceptionListType,
ExceptionListItemSchema,
ExceptionIdentifiers,
ExceptionListIdentifiers,
Pagination,
} from '../../../../../public/lists_plugin_deps';
@ -36,7 +36,7 @@ export interface State {
export type Action =
| {
type: 'setExceptions';
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
exceptions: ExceptionListItemSchema[];
pagination: Pagination;
}
@ -48,7 +48,7 @@ export type Action =
| { type: 'updateModalOpen'; modalName: ViewerModalName }
| {
type: 'updateExceptionToEdit';
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
exception: ExceptionListItemSchema;
}
| { type: 'updateLoadingItemIds'; items: ExceptionListItemIdentifiers[] }

View file

@ -54,6 +54,7 @@ interface OwnProps {
hasIndexWrite: boolean;
from: string;
loading: boolean;
onRuleChange?: () => void;
showBuildingBlockAlerts: boolean;
onShowBuildingBlockAlertsChanged: (showBuildingBlockAlerts: boolean) => void;
to: string;
@ -75,6 +76,7 @@ export const AlertsTableComponent: React.FC<AlertsTableComponentProps> = ({
isSelectAllChecked,
loading,
loadingEventIds,
onRuleChange,
selectedEventIds,
setEventsDeleted,
setEventsLoading,
@ -330,6 +332,7 @@ export const AlertsTableComponent: React.FC<AlertsTableComponentProps> = ({
end={to}
headerFilterGroup={headerFilterGroup}
id={timelineId}
onRuleChange={onRuleChange}
scopeId={SourcererScopeName.detections}
start={from}
utilityBar={utilityBarCallback}

View file

@ -29,7 +29,7 @@ import { FILTER_OPEN, FILTER_CLOSED, FILTER_IN_PROGRESS } from '../alerts_filter
import { updateAlertStatusAction } from '../actions';
import { SetEventsDeletedProps, SetEventsLoadingProps } from '../types';
import { Ecs } from '../../../../../common/ecs';
import { AddExceptionModal as AddExceptionModalComponent } from '../../../../common/components/exceptions/add_exception_modal';
import { AddExceptionModal } from '../../../../common/components/exceptions/add_exception_modal';
import * as i18nCommon from '../../../../common/translations';
import * as i18n from '../translations';
import {
@ -45,6 +45,7 @@ interface AlertContextMenuProps {
disabled: boolean;
ecsRowData: Ecs;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
timelineId: string;
}
@ -52,6 +53,7 @@ const AlertContextMenuComponent: React.FC<AlertContextMenuProps> = ({
disabled,
ecsRowData,
refetch,
onRuleChange,
timelineId,
}) => {
const dispatch = useDispatch();
@ -376,7 +378,7 @@ const AlertContextMenuComponent: React.FC<AlertContextMenuProps> = ({
</EventsTdContent>
</EventsTd>
{exceptionModalType != null && ruleId != null && ecsRowData != null && (
<AddExceptionModalComponent
<AddExceptionModal
ruleName={ruleName}
ruleId={ruleId}
ruleIndices={ruleIndices}
@ -385,6 +387,7 @@ const AlertContextMenuComponent: React.FC<AlertContextMenuProps> = ({
onCancel={onAddExceptionCancel}
onConfirm={onAddExceptionConfirm}
alertStatus={alertStatus}
onRuleChange={onRuleChange}
/>
)}
</>

View file

@ -79,7 +79,7 @@ import { ExceptionsViewer } from '../../../../../common/components/exceptions/vi
import { DEFAULT_INDEX_PATTERN } from '../../../../../../common/constants';
import { useFullScreen } from '../../../../../common/containers/use_full_screen';
import { Display } from '../../../../../hosts/pages/display';
import { ExceptionListTypeEnum, ExceptionIdentifiers } from '../../../../../shared_imports';
import { ExceptionListTypeEnum, ExceptionListIdentifiers } from '../../../../../shared_imports';
import { isMlRule } from '../../../../../../common/machine_learning/helpers';
import { isThresholdRule } from '../../../../../../common/detection_engine/utils';
import { useRuleAsync } from '../../../../containers/detection_engine/rules/use_rule_async';
@ -354,12 +354,12 @@ export const RuleDetailsPageComponent: FC<PropsFromRedux> = ({
const { indicesExist, indexPattern } = useSourcererScope(SourcererScopeName.detections);
const exceptionLists = useMemo((): {
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
allowedExceptionListTypes: ExceptionListTypeEnum[];
} => {
if (rule != null && rule.exceptions_list != null) {
return rule.exceptions_list.reduce<{
lists: ExceptionIdentifiers[];
lists: ExceptionListIdentifiers[];
allowedExceptionListTypes: ExceptionListTypeEnum[];
}>(
(acc, { id, list_id: listId, namespace_type: namespaceType, type }) => {
@ -542,6 +542,7 @@ export const RuleDetailsPageComponent: FC<PropsFromRedux> = ({
loading={loading}
showBuildingBlockAlerts={showBuildingBlockAlerts}
onShowBuildingBlockAlertsChanged={onShowBuildingBlockAlertsChangedCallback}
onRuleChange={refreshRule}
to={to}
/>
)}

View file

@ -49,7 +49,7 @@ export {
updateExceptionListItem,
fetchExceptionListById,
addExceptionList,
ExceptionIdentifiers,
ExceptionListIdentifiers,
ExceptionList,
Pagination,
UseExceptionListSuccess,

View file

@ -54,6 +54,7 @@ interface Props {
onRowSelected: OnRowSelected;
onUnPinEvent: OnUnPinEvent;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
selectedEventIds: Readonly<Record<string, TimelineNonEcsData[]>>;
showCheckboxes: boolean;
showNotes: boolean;
@ -88,6 +89,7 @@ export const EventColumnView = React.memo<Props>(
onRowSelected,
onUnPinEvent,
refetch,
onRuleChange,
selectedEventIds,
showCheckboxes,
showNotes,
@ -157,6 +159,7 @@ export const EventColumnView = React.memo<Props>(
timelineId={timelineId}
disabled={eventType !== 'signal'}
refetch={refetch}
onRuleChange={onRuleChange}
/>,
],
[
@ -171,6 +174,7 @@ export const EventColumnView = React.memo<Props>(
isEventPinned,
isEventViewer,
refetch,
onRuleChange,
showNotes,
status,
timelineId,

View file

@ -49,6 +49,7 @@ interface Props {
onUnPinEvent: OnUnPinEvent;
pinnedEventIds: Readonly<Record<string, boolean>>;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
rowRenderers: RowRenderer[];
selectedEventIds: Readonly<Record<string, TimelineNonEcsData[]>>;
showCheckboxes: boolean;
@ -77,6 +78,7 @@ const EventsComponent: React.FC<Props> = ({
onUnPinEvent,
pinnedEventIds,
refetch,
onRuleChange,
rowRenderers,
selectedEventIds,
showCheckboxes,
@ -108,6 +110,7 @@ const EventsComponent: React.FC<Props> = ({
onUpdateColumns={onUpdateColumns}
refetch={refetch}
rowRenderers={rowRenderers}
onRuleChange={onRuleChange}
selectedEventIds={selectedEventIds}
showCheckboxes={showCheckboxes}
timelineId={id}

View file

@ -60,6 +60,7 @@ interface Props {
onUpdateColumns: OnUpdateColumns;
isEventPinned: boolean;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
rowRenderers: RowRenderer[];
selectedEventIds: Readonly<Record<string, TimelineNonEcsData[]>>;
showCheckboxes: boolean;
@ -129,6 +130,7 @@ const StatefulEventComponent: React.FC<Props> = ({
onUnPinEvent,
onUpdateColumns,
refetch,
onRuleChange,
rowRenderers,
selectedEventIds,
showCheckboxes,
@ -208,6 +210,7 @@ const StatefulEventComponent: React.FC<Props> = ({
onRowSelected={onRowSelected}
onUnPinEvent={onUnPinEvent}
refetch={refetch}
onRuleChange={onRuleChange}
selectedEventIds={selectedEventIds}
showCheckboxes={showCheckboxes}
showNotes={!!showNotes[event._id]}
@ -296,6 +299,7 @@ const StatefulEventComponent: React.FC<Props> = ({
onUnPinEvent,
onUpdateColumns,
refetch,
onRuleChange,
rowRenderers,
selectedEventIds,
showCheckboxes,

View file

@ -57,6 +57,7 @@ export interface BodyProps {
onUnPinEvent: OnUnPinEvent;
pinnedEventIds: Readonly<Record<string, boolean>>;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
rowRenderers: RowRenderer[];
selectedEventIds: Readonly<Record<string, TimelineNonEcsData[]>>;
show: boolean;
@ -101,6 +102,7 @@ export const Body = React.memo<BodyProps>(
pinnedEventIds,
rowRenderers,
refetch,
onRuleChange,
selectedEventIds,
show,
showCheckboxes,
@ -186,6 +188,7 @@ export const Body = React.memo<BodyProps>(
pinnedEventIds={pinnedEventIds}
refetch={refetch}
rowRenderers={rowRenderers}
onRuleChange={onRuleChange}
selectedEventIds={selectedEventIds}
showCheckboxes={showCheckboxes}
toggleColumn={toggleColumn}

View file

@ -46,6 +46,7 @@ interface OwnProps {
sort: Sort;
toggleColumn: (column: ColumnHeaderOptions) => void;
refetch: inputsModel.Refetch;
onRuleChange?: () => void;
}
type StatefulBodyComponentProps = OwnProps & PropsFromRedux;
@ -73,6 +74,7 @@ const StatefulBodyComponent = React.memo<StatefulBodyComponentProps>(
selectedEventIds,
setSelected,
clearSelected,
onRuleChange,
show,
showCheckboxes,
graphEventId,
@ -211,6 +213,7 @@ const StatefulBodyComponent = React.memo<StatefulBodyComponentProps>(
onUpdateColumns={onUpdateColumns}
pinnedEventIds={pinnedEventIds}
refetch={refetch}
onRuleChange={onRuleChange}
rowRenderers={enabledRowRenderers}
selectedEventIds={selectedEventIds}
show={id === TimelineId.active ? show : true}