[Osquery] Fix 7.14 live query history view (#105211)
This commit is contained in:
parent
0c9777c602
commit
3e5ed77470
|
@ -8,15 +8,13 @@
|
||||||
/* eslint-disable @typescript-eslint/no-unused-vars */
|
/* eslint-disable @typescript-eslint/no-unused-vars */
|
||||||
|
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { EuiLink, EuiInMemoryTable, EuiCodeBlock } from '@elastic/eui';
|
import { EuiInMemoryTable, EuiCodeBlock } from '@elastic/eui';
|
||||||
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
||||||
|
|
||||||
import { PLUGIN_ID } from '../../../fleet/common';
|
import { AgentIdToName } from '../agents/agent_id_to_name';
|
||||||
import { pagePathGetters } from '../../../fleet/public';
|
|
||||||
import { useActionResults } from './use_action_results';
|
import { useActionResults } from './use_action_results';
|
||||||
import { useAllResults } from '../results/use_all_results';
|
import { useAllResults } from '../results/use_all_results';
|
||||||
import { Direction } from '../../common/search_strategy';
|
import { Direction } from '../../common/search_strategy';
|
||||||
import { useKibana } from '../common/lib/kibana';
|
|
||||||
|
|
||||||
interface ActionResultsSummaryProps {
|
interface ActionResultsSummaryProps {
|
||||||
actionId: string;
|
actionId: string;
|
||||||
|
@ -35,7 +33,6 @@ const ActionResultsSummaryComponent: React.FC<ActionResultsSummaryProps> = ({
|
||||||
expirationDate,
|
expirationDate,
|
||||||
agentIds,
|
agentIds,
|
||||||
}) => {
|
}) => {
|
||||||
const getUrlForApp = useKibana().services.application.getUrlForApp;
|
|
||||||
// @ts-expect-error update types
|
// @ts-expect-error update types
|
||||||
const [pageIndex, setPageIndex] = useState(0);
|
const [pageIndex, setPageIndex] = useState(0);
|
||||||
// @ts-expect-error update types
|
// @ts-expect-error update types
|
||||||
|
@ -70,20 +67,7 @@ const ActionResultsSummaryComponent: React.FC<ActionResultsSummaryProps> = ({
|
||||||
isLive,
|
isLive,
|
||||||
});
|
});
|
||||||
|
|
||||||
const renderAgentIdColumn = useCallback(
|
const renderAgentIdColumn = useCallback((agentId) => <AgentIdToName agentId={agentId} />, []);
|
||||||
(agentId) => (
|
|
||||||
<EuiLink
|
|
||||||
className="eui-textTruncate"
|
|
||||||
href={getUrlForApp(PLUGIN_ID, {
|
|
||||||
path: `#` + pagePathGetters.agent_details({ agentId })[1],
|
|
||||||
})}
|
|
||||||
target="_blank"
|
|
||||||
>
|
|
||||||
{agentId}
|
|
||||||
</EuiLink>
|
|
||||||
),
|
|
||||||
[getUrlForApp]
|
|
||||||
);
|
|
||||||
|
|
||||||
const renderRowsColumn = useCallback(
|
const renderRowsColumn = useCallback(
|
||||||
(_, item) => {
|
(_, item) => {
|
||||||
|
|
|
@ -9,6 +9,7 @@ import { isArray } from 'lodash';
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { EuiBasicTable, EuiButtonIcon, EuiCodeBlock, formatDate } from '@elastic/eui';
|
import { EuiBasicTable, EuiButtonIcon, EuiCodeBlock, formatDate } from '@elastic/eui';
|
||||||
import React, { useState, useCallback, useMemo } from 'react';
|
import React, { useState, useCallback, useMemo } from 'react';
|
||||||
|
import { useHistory } from 'react-router-dom';
|
||||||
|
|
||||||
import { useAllActions } from './use_all_actions';
|
import { useAllActions } from './use_all_actions';
|
||||||
import { Direction } from '../../common/search_strategy';
|
import { Direction } from '../../common/search_strategy';
|
||||||
|
@ -27,6 +28,7 @@ const ActionTableResultsButton = React.memo<ActionTableResultsButtonProps>(({ ac
|
||||||
ActionTableResultsButton.displayName = 'ActionTableResultsButton';
|
ActionTableResultsButton.displayName = 'ActionTableResultsButton';
|
||||||
|
|
||||||
const ActionsTableComponent = () => {
|
const ActionsTableComponent = () => {
|
||||||
|
const { push } = useHistory();
|
||||||
const [pageIndex, setPageIndex] = useState(0);
|
const [pageIndex, setPageIndex] = useState(0);
|
||||||
const [pageSize, setPageSize] = useState(20);
|
const [pageSize, setPageSize] = useState(20);
|
||||||
|
|
||||||
|
@ -67,6 +69,16 @@ const ActionsTableComponent = () => {
|
||||||
[]
|
[]
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const handlePlayClick = useCallback(
|
||||||
|
(item) =>
|
||||||
|
push('/live_queries/new', {
|
||||||
|
form: {
|
||||||
|
query: item._source?.data?.query,
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
[push]
|
||||||
|
);
|
||||||
|
|
||||||
const columns = useMemo(
|
const columns = useMemo(
|
||||||
() => [
|
() => [
|
||||||
{
|
{
|
||||||
|
@ -106,6 +118,11 @@ const ActionsTableComponent = () => {
|
||||||
defaultMessage: 'View details',
|
defaultMessage: 'View details',
|
||||||
}),
|
}),
|
||||||
actions: [
|
actions: [
|
||||||
|
{
|
||||||
|
type: 'icon',
|
||||||
|
icon: 'play',
|
||||||
|
onClick: handlePlayClick,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
render: renderActionsColumn,
|
render: renderActionsColumn,
|
||||||
},
|
},
|
||||||
|
@ -113,6 +130,7 @@ const ActionsTableComponent = () => {
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
[
|
[
|
||||||
|
handlePlayClick,
|
||||||
renderActionsColumn,
|
renderActionsColumn,
|
||||||
renderAgentsColumn,
|
renderAgentsColumn,
|
||||||
renderCreatedByColumn,
|
renderCreatedByColumn,
|
||||||
|
@ -135,6 +153,7 @@ const ActionsTableComponent = () => {
|
||||||
<EuiBasicTable
|
<EuiBasicTable
|
||||||
// eslint-disable-next-line react-perf/jsx-no-new-array-as-prop
|
// eslint-disable-next-line react-perf/jsx-no-new-array-as-prop
|
||||||
items={actionsData?.actions ?? []}
|
items={actionsData?.actions ?? []}
|
||||||
|
// @ts-expect-error update types
|
||||||
columns={columns}
|
columns={columns}
|
||||||
pagination={pagination}
|
pagination={pagination}
|
||||||
onChange={onTableChange}
|
onChange={onTableChange}
|
||||||
|
|
37
x-pack/plugins/osquery/public/agents/agent_id_to_name.tsx
Normal file
37
x-pack/plugins/osquery/public/agents/agent_id_to_name.tsx
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
/*
|
||||||
|
* 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 { EuiLink } from '@elastic/eui';
|
||||||
|
import React from 'react';
|
||||||
|
|
||||||
|
import { useAgentDetails } from './use_agent_details';
|
||||||
|
import { PLUGIN_ID } from '../../../fleet/common';
|
||||||
|
import { pagePathGetters } from '../../../fleet/public';
|
||||||
|
import { useKibana } from '../common/lib/kibana';
|
||||||
|
|
||||||
|
interface AgentIdToNameProps {
|
||||||
|
agentId: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
const AgentIdToNameComponent: React.FC<AgentIdToNameProps> = ({ agentId }) => {
|
||||||
|
const getUrlForApp = useKibana().services.application.getUrlForApp;
|
||||||
|
const { data } = useAgentDetails({ agentId });
|
||||||
|
|
||||||
|
return (
|
||||||
|
<EuiLink
|
||||||
|
className="eui-textTruncate"
|
||||||
|
href={getUrlForApp(PLUGIN_ID, {
|
||||||
|
path: `#` + pagePathGetters.agent_details({ agentId })[1],
|
||||||
|
})}
|
||||||
|
target="_blank"
|
||||||
|
>
|
||||||
|
{data?.item.local_metadata.host.name ?? agentId}
|
||||||
|
</EuiLink>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export const AgentIdToName = React.memo(AgentIdToNameComponent);
|
|
@ -21,7 +21,12 @@ import {
|
||||||
generateAgentSelection,
|
generateAgentSelection,
|
||||||
} from './helpers';
|
} from './helpers';
|
||||||
|
|
||||||
import { SELECT_AGENT_LABEL, generateSelectedAgentsMessage } from './translations';
|
import {
|
||||||
|
SELECT_AGENT_LABEL,
|
||||||
|
generateSelectedAgentsMessage,
|
||||||
|
ALL_AGENTS_LABEL,
|
||||||
|
AGENT_POLICY_LABEL,
|
||||||
|
} from './translations';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
AGENT_GROUP_KEY,
|
AGENT_GROUP_KEY,
|
||||||
|
@ -72,8 +77,17 @@ const AgentsTableComponent: React.FC<AgentsTableProps> = ({ agentSelection, onCh
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (agentSelection && !defaultValueInitialized.current && options.length) {
|
if (agentSelection && !defaultValueInitialized.current && options.length) {
|
||||||
if (agentSelection.policiesSelected) {
|
if (agentSelection.allAgentsSelected) {
|
||||||
const policyOptions = find(['label', 'Policy'], options);
|
const allAgentsOptions = find(['label', ALL_AGENTS_LABEL], options);
|
||||||
|
|
||||||
|
if (allAgentsOptions?.options) {
|
||||||
|
setSelectedOptions(allAgentsOptions.options);
|
||||||
|
defaultValueInitialized.current = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (agentSelection.policiesSelected.length) {
|
||||||
|
const policyOptions = find(['label', AGENT_POLICY_LABEL], options);
|
||||||
|
|
||||||
if (policyOptions) {
|
if (policyOptions) {
|
||||||
const defaultOptions = policyOptions.options?.filter((option) =>
|
const defaultOptions = policyOptions.options?.filter((option) =>
|
||||||
|
@ -82,12 +96,12 @@ const AgentsTableComponent: React.FC<AgentsTableProps> = ({ agentSelection, onCh
|
||||||
|
|
||||||
if (defaultOptions?.length) {
|
if (defaultOptions?.length) {
|
||||||
setSelectedOptions(defaultOptions);
|
setSelectedOptions(defaultOptions);
|
||||||
|
defaultValueInitialized.current = true;
|
||||||
}
|
}
|
||||||
defaultValueInitialized.current = true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}, [agentSelection, options]);
|
}, [agentSelection, options, selectedOptions]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
// update the groups when groups or agents have changed
|
// update the groups when groups or agents have changed
|
||||||
|
|
36
x-pack/plugins/osquery/public/agents/use_agent_details.ts
Normal file
36
x-pack/plugins/osquery/public/agents/use_agent_details.ts
Normal file
|
@ -0,0 +1,36 @@
|
||||||
|
/*
|
||||||
|
* 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 { useQuery } from 'react-query';
|
||||||
|
|
||||||
|
import { GetOneAgentResponse, agentRouteService } from '../../../fleet/common';
|
||||||
|
import { useErrorToast } from '../common/hooks/use_error_toast';
|
||||||
|
import { useKibana } from '../common/lib/kibana';
|
||||||
|
|
||||||
|
interface UseAgentDetails {
|
||||||
|
agentId: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAgentDetails = ({ agentId }: UseAgentDetails) => {
|
||||||
|
const { http } = useKibana().services;
|
||||||
|
const setErrorToast = useErrorToast();
|
||||||
|
return useQuery<GetOneAgentResponse>(
|
||||||
|
['agentDetails', agentId],
|
||||||
|
() => http.get(agentRouteService.getInfoPath(agentId)),
|
||||||
|
{
|
||||||
|
enabled: agentId.length > 0,
|
||||||
|
onSuccess: () => setErrorToast(),
|
||||||
|
onError: (error) =>
|
||||||
|
setErrorToast(error as Error, {
|
||||||
|
title: i18n.translate('xpack.osquery.agentDetails.fetchError', {
|
||||||
|
defaultMessage: 'Error while fetching agent details',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
};
|
|
@ -38,7 +38,7 @@ export const useAllAgents = (
|
||||||
let kuery = `last_checkin_status: online and (${policyFragment})`;
|
let kuery = `last_checkin_status: online and (${policyFragment})`;
|
||||||
|
|
||||||
if (searchValue) {
|
if (searchValue) {
|
||||||
kuery += `and (local_metadata.host.hostname:*${searchValue}* or local_metadata.elastic.agent.id:*${searchValue}*)`;
|
kuery += ` and (local_metadata.host.hostname:*${searchValue}* or local_metadata.elastic.agent.id:*${searchValue}*)`;
|
||||||
}
|
}
|
||||||
|
|
||||||
return http.get(agentRouteService.getListPath(), {
|
return http.get(agentRouteService.getListPath(), {
|
||||||
|
|
|
@ -110,7 +110,7 @@ const LiveQueryFormComponent: React.FC<LiveQueryFormProps> = ({
|
||||||
{
|
{
|
||||||
agentSelection: {
|
agentSelection: {
|
||||||
agents: [],
|
agents: [],
|
||||||
allAgentsSelected: false,
|
allAgentsSelected: true,
|
||||||
platformsSelected: [],
|
platformsSelected: [],
|
||||||
policiesSelected: [],
|
policiesSelected: [],
|
||||||
},
|
},
|
||||||
|
|
|
@ -8,7 +8,7 @@
|
||||||
import { EuiButtonEmpty, EuiFlexGroup, EuiFlexItem } from '@elastic/eui';
|
import { EuiButtonEmpty, EuiFlexGroup, EuiFlexItem } from '@elastic/eui';
|
||||||
import { FormattedMessage } from '@kbn/i18n/react';
|
import { FormattedMessage } from '@kbn/i18n/react';
|
||||||
import React, { useMemo } from 'react';
|
import React, { useMemo } from 'react';
|
||||||
import { useLocation } from 'react-router-dom';
|
import { useHistory, useLocation } from 'react-router-dom';
|
||||||
import qs from 'query-string';
|
import qs from 'query-string';
|
||||||
|
|
||||||
import { WithHeaderLayout } from '../../../components/layouts';
|
import { WithHeaderLayout } from '../../../components/layouts';
|
||||||
|
@ -19,12 +19,18 @@ import { BetaBadge, BetaBadgeRowWrapper } from '../../../components/beta_badge';
|
||||||
|
|
||||||
const NewLiveQueryPageComponent = () => {
|
const NewLiveQueryPageComponent = () => {
|
||||||
useBreadcrumbs('live_query_new');
|
useBreadcrumbs('live_query_new');
|
||||||
|
const { replace } = useHistory();
|
||||||
const location = useLocation();
|
const location = useLocation();
|
||||||
const liveQueryListProps = useRouterNavigate('live_queries');
|
const liveQueryListProps = useRouterNavigate('live_queries');
|
||||||
|
|
||||||
const formDefaultValue = useMemo(() => {
|
const formDefaultValue = useMemo(() => {
|
||||||
const queryParams = qs.parse(location.search);
|
const queryParams = qs.parse(location.search);
|
||||||
|
|
||||||
|
if (location.state?.form.query) {
|
||||||
|
replace({ state: null });
|
||||||
|
return { query: location.state?.form.query };
|
||||||
|
}
|
||||||
|
|
||||||
if (queryParams?.agentPolicyId) {
|
if (queryParams?.agentPolicyId) {
|
||||||
return {
|
return {
|
||||||
agentSelection: {
|
agentSelection: {
|
||||||
|
@ -37,7 +43,7 @@ const NewLiveQueryPageComponent = () => {
|
||||||
}
|
}
|
||||||
|
|
||||||
return undefined;
|
return undefined;
|
||||||
}, [location.search]);
|
}, [location.search, location.state, replace]);
|
||||||
|
|
||||||
const LeftColumn = useMemo(
|
const LeftColumn = useMemo(
|
||||||
() => (
|
() => (
|
||||||
|
|
|
@ -16,6 +16,7 @@ import {
|
||||||
import React, { useCallback, useMemo, useState } from 'react';
|
import React, { useCallback, useMemo, useState } from 'react';
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { FormattedMessage } from '@kbn/i18n/react';
|
import { FormattedMessage } from '@kbn/i18n/react';
|
||||||
|
import { useHistory } from 'react-router-dom';
|
||||||
|
|
||||||
import { SavedObject } from 'kibana/public';
|
import { SavedObject } from 'kibana/public';
|
||||||
import { WithHeaderLayout } from '../../../components/layouts';
|
import { WithHeaderLayout } from '../../../components/layouts';
|
||||||
|
@ -51,6 +52,7 @@ const EditButton = React.memo(EditButtonComponent);
|
||||||
|
|
||||||
const SavedQueriesPageComponent = () => {
|
const SavedQueriesPageComponent = () => {
|
||||||
useBreadcrumbs('saved_queries');
|
useBreadcrumbs('saved_queries');
|
||||||
|
const { push } = useHistory();
|
||||||
const newQueryLinkProps = useRouterNavigate('saved_queries/new');
|
const newQueryLinkProps = useRouterNavigate('saved_queries/new');
|
||||||
const [pageIndex, setPageIndex] = useState(0);
|
const [pageIndex, setPageIndex] = useState(0);
|
||||||
const [pageSize, setPageSize] = useState(10);
|
const [pageSize, setPageSize] = useState(10);
|
||||||
|
@ -59,21 +61,15 @@ const SavedQueriesPageComponent = () => {
|
||||||
|
|
||||||
const { data } = useSavedQueries({ isLive: true });
|
const { data } = useSavedQueries({ isLive: true });
|
||||||
|
|
||||||
// const handlePlayClick = useCallback(
|
const handlePlayClick = useCallback(
|
||||||
// (item) =>
|
(item) =>
|
||||||
// push({
|
push('/live_queries/new', {
|
||||||
// search: qs.stringify({
|
form: {
|
||||||
// tab: 'live_query',
|
savedQueryId: item.id,
|
||||||
// }),
|
},
|
||||||
// state: {
|
}),
|
||||||
// query: {
|
[push]
|
||||||
// id: item.id,
|
);
|
||||||
// query: item.attributes.query,
|
|
||||||
// },
|
|
||||||
// },
|
|
||||||
// }),
|
|
||||||
// [push]
|
|
||||||
// );
|
|
||||||
|
|
||||||
const renderEditAction = useCallback(
|
const renderEditAction = useCallback(
|
||||||
(item: SavedObject<{ name: string }>) => (
|
(item: SavedObject<{ name: string }>) => (
|
||||||
|
@ -96,45 +92,53 @@ const SavedQueriesPageComponent = () => {
|
||||||
() => [
|
() => [
|
||||||
{
|
{
|
||||||
field: 'attributes.id',
|
field: 'attributes.id',
|
||||||
name: 'Query ID',
|
name: i18n.translate('xpack.osquery.savedQueries.table.queryIdColumnTitle', {
|
||||||
|
defaultMessage: 'Query ID',
|
||||||
|
}),
|
||||||
sortable: true,
|
sortable: true,
|
||||||
truncateText: true,
|
truncateText: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
field: 'attributes.description',
|
field: 'attributes.description',
|
||||||
name: 'Description',
|
name: i18n.translate('xpack.osquery.savedQueries.table.descriptionColumnTitle', {
|
||||||
|
defaultMessage: 'Description',
|
||||||
|
}),
|
||||||
sortable: true,
|
sortable: true,
|
||||||
truncateText: true,
|
truncateText: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
field: 'attributes.created_by',
|
field: 'attributes.created_by',
|
||||||
name: 'Created by',
|
name: i18n.translate('xpack.osquery.savedQueries.table.createdByColumnTitle', {
|
||||||
|
defaultMessage: 'Created by',
|
||||||
|
}),
|
||||||
sortable: true,
|
sortable: true,
|
||||||
truncateText: true,
|
truncateText: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
field: 'attributes.updated_at',
|
field: 'attributes.updated_at',
|
||||||
name: 'Last updated at',
|
name: i18n.translate('xpack.osquery.savedQueries.table.updatedAtColumnTitle', {
|
||||||
|
defaultMessage: 'Last updated at',
|
||||||
|
}),
|
||||||
sortable: (item: SavedObject<{ updated_at: string }>) =>
|
sortable: (item: SavedObject<{ updated_at: string }>) =>
|
||||||
item.attributes.updated_at ? Date.parse(item.attributes.updated_at) : 0,
|
item.attributes.updated_at ? Date.parse(item.attributes.updated_at) : 0,
|
||||||
truncateText: true,
|
truncateText: true,
|
||||||
render: renderUpdatedAt,
|
render: renderUpdatedAt,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'Actions',
|
name: i18n.translate('xpack.osquery.savedQueries.table.actionsColumnTitle', {
|
||||||
|
defaultMessage: 'Actions',
|
||||||
|
}),
|
||||||
actions: [
|
actions: [
|
||||||
// {
|
{
|
||||||
// name: 'Live query',
|
type: 'icon',
|
||||||
// description: 'Run live query',
|
icon: 'play',
|
||||||
// type: 'icon',
|
onClick: handlePlayClick,
|
||||||
// icon: 'play',
|
},
|
||||||
// onClick: handlePlayClick,
|
|
||||||
// },
|
|
||||||
{ render: renderEditAction },
|
{ render: renderEditAction },
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
[renderEditAction, renderUpdatedAt]
|
[handlePlayClick, renderEditAction, renderUpdatedAt]
|
||||||
);
|
);
|
||||||
|
|
||||||
const onTableChange = useCallback(({ page = {}, sort = {} }) => {
|
const onTableChange = useCallback(({ page = {}, sort = {} }) => {
|
||||||
|
|
|
@ -7,10 +7,11 @@
|
||||||
|
|
||||||
import { find } from 'lodash/fp';
|
import { find } from 'lodash/fp';
|
||||||
import { EuiCodeBlock, EuiFormRow, EuiComboBox, EuiText } from '@elastic/eui';
|
import { EuiCodeBlock, EuiFormRow, EuiComboBox, EuiText } from '@elastic/eui';
|
||||||
import React, { useCallback, useState } from 'react';
|
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
||||||
import { SimpleSavedObject } from 'kibana/public';
|
import { SimpleSavedObject } from 'kibana/public';
|
||||||
import { i18n } from '@kbn/i18n';
|
import { i18n } from '@kbn/i18n';
|
||||||
import { FormattedMessage } from '@kbn/i18n/react';
|
import { FormattedMessage } from '@kbn/i18n/react';
|
||||||
|
import { useHistory, useLocation } from 'react-router-dom';
|
||||||
|
|
||||||
import { useSavedQueries } from './use_saved_queries';
|
import { useSavedQueries } from './use_saved_queries';
|
||||||
|
|
||||||
|
@ -29,19 +30,25 @@ const SavedQueriesDropdownComponent: React.FC<SavedQueriesDropdownProps> = ({
|
||||||
disabled,
|
disabled,
|
||||||
onChange,
|
onChange,
|
||||||
}) => {
|
}) => {
|
||||||
|
const { replace } = useHistory();
|
||||||
|
const location = useLocation();
|
||||||
const [selectedOptions, setSelectedOptions] = useState([]);
|
const [selectedOptions, setSelectedOptions] = useState([]);
|
||||||
|
|
||||||
const { data } = useSavedQueries({});
|
const { data } = useSavedQueries({});
|
||||||
|
|
||||||
const queryOptions =
|
const queryOptions = useMemo(
|
||||||
data?.savedObjects?.map((savedQuery) => ({
|
() =>
|
||||||
label: savedQuery.attributes.id ?? '',
|
data?.savedObjects?.map((savedQuery) => ({
|
||||||
value: {
|
label: savedQuery.attributes.id ?? '',
|
||||||
id: savedQuery.attributes.id,
|
value: {
|
||||||
description: savedQuery.attributes.description,
|
savedObjectId: savedQuery.id,
|
||||||
query: savedQuery.attributes.query,
|
id: savedQuery.attributes.id,
|
||||||
},
|
description: savedQuery.attributes.description,
|
||||||
})) ?? [];
|
query: savedQuery.attributes.query,
|
||||||
|
},
|
||||||
|
})) ?? [],
|
||||||
|
[data?.savedObjects]
|
||||||
|
);
|
||||||
|
|
||||||
const handleSavedQueryChange = useCallback(
|
const handleSavedQueryChange = useCallback(
|
||||||
(newSelectedOptions) => {
|
(newSelectedOptions) => {
|
||||||
|
@ -73,6 +80,20 @@ const SavedQueriesDropdownComponent: React.FC<SavedQueriesDropdownProps> = ({
|
||||||
[]
|
[]
|
||||||
);
|
);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const savedQueryId = location.state?.form?.savedQueryId;
|
||||||
|
|
||||||
|
if (savedQueryId) {
|
||||||
|
const savedQueryOption = find(['value.savedObjectId', savedQueryId], queryOptions);
|
||||||
|
|
||||||
|
if (savedQueryOption) {
|
||||||
|
handleSavedQueryChange([savedQueryOption]);
|
||||||
|
}
|
||||||
|
|
||||||
|
replace({ state: null });
|
||||||
|
}
|
||||||
|
}, [handleSavedQueryChange, replace, location.state, queryOptions]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<EuiFormRow
|
<EuiFormRow
|
||||||
label={
|
label={
|
||||||
|
|
|
@ -258,7 +258,7 @@ const ViewResultsInDiscoverActionComponent: React.FC<ViewResultsInDiscoverAction
|
||||||
}
|
}
|
||||||
: {
|
: {
|
||||||
to: 'now',
|
to: 'now',
|
||||||
from: 'now-15m',
|
from: 'now-1d',
|
||||||
mode: 'relative',
|
mode: 'relative',
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -5,6 +5,8 @@
|
||||||
* 2.0.
|
* 2.0.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
import type { estypes } from '@elastic/elasticsearch';
|
||||||
|
|
||||||
import { ISearchRequestParams } from '../../../../../../../../../src/plugins/data/common';
|
import { ISearchRequestParams } from '../../../../../../../../../src/plugins/data/common';
|
||||||
import { AgentsRequestOptions } from '../../../../../../common/search_strategy';
|
import { AgentsRequestOptions } from '../../../../../../common/search_strategy';
|
||||||
// import { createQueryFilterClauses } from '../../../../../../common/utils/build_query';
|
// import { createQueryFilterClauses } from '../../../../../../common/utils/build_query';
|
||||||
|
@ -24,10 +26,23 @@ export const buildActionsQuery = ({
|
||||||
body: {
|
body: {
|
||||||
// query: { bool: { filter } },
|
// query: { bool: { filter } },
|
||||||
query: {
|
query: {
|
||||||
term: {
|
bool: {
|
||||||
type: {
|
must: [
|
||||||
value: 'INPUT_ACTION',
|
{
|
||||||
},
|
term: {
|
||||||
|
type: {
|
||||||
|
value: 'INPUT_ACTION',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
term: {
|
||||||
|
input_type: {
|
||||||
|
value: 'osquery',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
] as estypes.QueryDslQueryContainer[],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
from: cursorStart,
|
from: cursorStart,
|
||||||
|
|
Loading…
Reference in a new issue