From dd50d8b493aec69f4089962d24b630038f191e40 Mon Sep 17 00:00:00 2001 From: Eric Wei Date: Thu, 7 Sep 2023 15:14:38 -0700 Subject: [PATCH] [Log Explorer] Remove top level tabs (#970) * remove unused files Signed-off-by: Eric Wei * missing snapshots Signed-off-by: Eric Wei * minimal changes to remove log explorer tab Signed-off-by: Eric * skip tab related tests Signed-off-by: Eric * update snapshots Signed-off-by: Eric * remove missed logging Signed-off-by: Eric * add path to constant Signed-off-by: Eric --------- Signed-off-by: Eric Wei Signed-off-by: Eric --- .../integration/1_event_analytics.spec.js | 11 +- common/constants/explorer.ts | 3 + common/types/explorer.ts | 4 +- public/components/common/search/search.tsx | 1 - .../event_analytics/explorer/explorer.tsx | 21 +-- .../event_analytics/explorer/log_explorer.tsx | 170 +++--------------- .../saved_query_table.test.tsx.snap | 22 ++- .../components/event_analytics/home/home.tsx | 54 +----- .../home/saved_objects_table.tsx | 7 +- public/components/event_analytics/index.tsx | 16 +- public/framework/redux/store/shared_state.ts | 5 +- 11 files changed, 53 insertions(+), 261 deletions(-) diff --git a/.cypress/integration/1_event_analytics.spec.js b/.cypress/integration/1_event_analytics.spec.js index cbbeeae47..f25987f4f 100644 --- a/.cypress/integration/1_event_analytics.spec.js +++ b/.cypress/integration/1_event_analytics.spec.js @@ -108,7 +108,8 @@ describe('Open flyout for a data row to see details', () => { }); }); -describe('Add/delete/switch explorer top level tabs', () => { +// skip for now due to tab removals +describe.skip('Add/delete/switch explorer top level tabs', () => { beforeEach(() => { landOnEventExplorer(); }); @@ -406,7 +407,7 @@ describe('Live tail stop automatically', () => { landOnEventExplorer(); }); - it('Moving to other tab should stop live tail automatically', () => { + it.skip('Moving to other tab should stop live tail automatically', () => { clearQuerySearchBoxText('searchAutocompleteTextArea'); cy.get('[data-test-subj="searchAutocompleteTextArea"]').type(TEST_QUERIES[1].query); cy.get('[data-test-subj=eventLiveTail]').click(); @@ -414,7 +415,7 @@ describe('Live tail stop automatically', () => { cy.get('.euiToastHeader__title').contains('On').should('exist'); }); - it('Add a new tab', () => { + it.skip('Add a new tab', () => { cy.get('[data-test-subj="eventExplorer__topLevelTabbing"]') .find('button.euiTab') .then((lists) => { @@ -426,7 +427,7 @@ describe('Live tail stop automatically', () => { }); }); - it('Click to switch to another tab', () => { + it.skip('Click to switch to another tab', () => { cy.get('[data-test-subj="eventExplorer__addNewTab"]', { timeout: COMMAND_TIMEOUT_LONG, }).click(); @@ -441,7 +442,7 @@ describe('Live tail stop automatically', () => { .should('have.class', 'euiTab-isSelected'); }); - it('Close current selected tab', () => { + it.skip('Close current selected tab', () => { cy.get('[data-test-subj="eventExplorer__addNewTab"]', { timeout: COMMAND_TIMEOUT_LONG, }).click(); diff --git a/common/constants/explorer.ts b/common/constants/explorer.ts index f586f5fca..97bf98631 100644 --- a/common/constants/explorer.ts +++ b/common/constants/explorer.ts @@ -7,10 +7,13 @@ import { htmlIdGenerator } from '@elastic/eui'; import { ThresholdUnitType } from '../../public/components/event_analytics/explorer/visualizations/config_panel/config_panes/config_controls/config_thresholds'; import { VIS_CHART_TYPES } from './shared'; +// URLs export const EVENT_ANALYTICS_DOCUMENTATION_URL = 'https://opensearch.org/docs/latest/observability-plugin/event-analytics/'; export const OPEN_TELEMETRY_LOG_CORRELATION_LINK = 'https://opentelemetry.io/docs/reference/specification/logs/overview/#log-correlation'; +export const LOG_EXPLORER_BASE_PATH = 'observability-logs#/explorer/'; + export const RAW_QUERY = 'rawQuery'; export const FINAL_QUERY = 'finalQuery'; export const SELECTED_DATE_RANGE = 'selectedDateRange'; diff --git a/common/types/explorer.ts b/common/types/explorer.ts index 9c5d5a943..6dbab6dae 100644 --- a/common/types/explorer.ts +++ b/common/types/explorer.ts @@ -92,9 +92,7 @@ export interface IExplorerFields { } export interface EmptyTabParams { - tabIds: string[] | undefined; - queries: any | undefined; - explorerData: any | undefined; + tabIds: string[]; } export interface ILogExplorerProps { diff --git a/public/components/common/search/search.tsx b/public/components/common/search/search.tsx index 2f30ab500..3f457ce21 100644 --- a/public/components/common/search/search.tsx +++ b/public/components/common/search/search.tsx @@ -17,7 +17,6 @@ import { EuiBadge, EuiContextMenuPanel, EuiToolTip, - EuiCallOut, } from '@elastic/eui'; import { DatePicker } from './date_picker'; import '@algolia/autocomplete-theme-classic'; diff --git a/public/components/event_analytics/explorer/explorer.tsx b/public/components/event_analytics/explorer/explorer.tsx index be6030da5..7f3ea3ff7 100644 --- a/public/components/event_analytics/explorer/explorer.tsx +++ b/public/components/event_analytics/explorer/explorer.tsx @@ -38,7 +38,6 @@ import { DATE_PICKER_FORMAT, DEFAULT_AVAILABILITY_QUERY, EVENT_ANALYTICS_DOCUMENTATION_URL, - NEW_TAB, PATTERNS_EXTRACTOR_REGEX, PATTERNS_REGEX, RAW_QUERY, @@ -52,7 +51,6 @@ import { SELECTED_TIMESTAMP, TAB_CHART_ID, TAB_CHART_TITLE, - TAB_CREATED_TYPE, TAB_EVENT_ID, TAB_EVENT_TITLE, TIME_INTERVAL_OPTIONS, @@ -347,17 +345,6 @@ export const Explorer = ({ }, [appBasedRef.current]); useEffect(() => { - let objectId; - if (queryRef.current![TAB_CREATED_TYPE] === NEW_TAB || appLogEvents) { - objectId = queryRef.current!.savedObjectId || ''; - } else { - objectId = queryRef.current!.savedObjectId || savedObjectId; - } - if (objectId) { - updateTabData(objectId); - } else { - fetchData(startTime, endTime); - } if ( routerContext && routerContext.searchParams.get(CREATE_TAB_PARAM_KEY) === CREATE_TAB_PARAM[TAB_CHART_ID] @@ -367,10 +354,8 @@ export const Explorer = ({ }, []); useEffect(() => { - if (appLogEvents) { - if (savedObjectId) { - updateTabData(savedObjectId); - } + if (savedObjectId) { + updateTabData(savedObjectId); } }, [savedObjectId]); @@ -642,7 +627,7 @@ export const Explorer = ({ isOverridingTimestamp, query, isLiveTailOnRef.current, - isOverridingPattern + isOverridingPattern, ]); const visualizations: IVisualizationContainerProps = useMemo(() => { diff --git a/public/components/event_analytics/explorer/log_explorer.tsx b/public/components/event_analytics/explorer/log_explorer.tsx index 4fced3eea..ca8398863 100644 --- a/public/components/event_analytics/explorer/log_explorer.tsx +++ b/public/components/event_analytics/explorer/log_explorer.tsx @@ -3,36 +3,21 @@ * SPDX-License-Identifier: Apache-2.0 */ /* eslint-disable react-hooks/exhaustive-deps */ - -import { - EuiIcon, - EuiTabbedContent, - EuiTabbedContentTab, - EuiText, - htmlIdGenerator, -} from '@elastic/eui'; -import $ from 'jquery'; -import { isEmpty, map } from 'lodash'; -import React, { useContext, useEffect, useMemo, useRef, useState } from 'react'; -import { useDispatch, useSelector } from 'react-redux'; +import { isEmpty } from 'lodash'; +import React, { useContext, useEffect, useRef, useState } from 'react'; +import { useSelector } from 'react-redux'; import { useHistory } from 'react-router-dom'; import { LogExplorerRouterContext } from '..'; import { APP_ANALYTICS_TAB_ID_REGEX, CREATE_TAB_PARAM_KEY, - NEW_TAB, - REDIRECT_TAB, - SAVED_OBJECT_ID, TAB_CHART_ID, TAB_EVENT_ID, - TAB_ID_TXT_PFX, - TAB_TITLE, } from '../../../../common/constants/explorer'; import { ILogExplorerProps } from '../../../../common/types/explorer'; -import { initializeTabData, removeTabData } from '../../application_analytics/helpers/utils'; import { selectQueryResult } from '../redux/slices/query_result_slice'; import { selectQueries } from '../redux/slices/query_slice'; -import { selectQueryTabs, setSelectedQueryTab } from '../redux/slices/query_tab_slice'; +import { selectQueryTabs } from '../redux/slices/query_tab_slice'; import { Explorer } from './explorer'; const searchBarConfigs = { @@ -60,11 +45,9 @@ export const LogExplorer = ({ }: ILogExplorerProps) => { const history = useHistory(); const routerContext = useContext(LogExplorerRouterContext); - const dispatch = useDispatch(); const tabIds = useSelector(selectQueryTabs).queryTabIds.filter( (tabid: string) => !tabid.match(APP_ANALYTICS_TAB_ID_REGEX) ); - const tabNames = useSelector(selectQueryTabs).tabNames; const queries = useSelector(selectQueries); const curSelectedTabId = useSelector(selectQueryTabs).selectedQueryTab; const explorerData = useSelector(selectQueryResult); @@ -79,68 +62,12 @@ export const LogExplorer = ({ const [tabCreatedTypes, setTabCreatedTypes] = useState({}); - // Append add-new-tab link to the end of the tab list, and remove it once tabs state changes - useEffect(() => { - const newLink = $( - '+ Add new' - ).on('click', () => { - addNewTab(NEW_TAB); - }); - $('.queryTabs > .euiTabs').append(newLink); - return () => { - $('.queryTabs > .euiTabs .linkNewTag').remove(); - }; - }, [tabIds]); - - const handleTabClick = (selectedTab: EuiTabbedContentTab) => { - history.replace(`/explorer/${queryRef.current![selectedTab.id][SAVED_OBJECT_ID] || ''}`); - dispatch(setSelectedQueryTab({ tabId: selectedTab.id })); - }; - - const handleTabClose = (TabIdToBeClosed: string) => { - if (tabIds.length === 1) { - setToast('Cannot close last tab.', 'danger'); - return; - } - - const index: number = tabIds.indexOf(TabIdToBeClosed); - const curSelectedTab = curSelectedTabIdRef.current; - let newIdToFocus = ''; - if (TabIdToBeClosed === curSelectedTab) { - if (index === 0) { - newIdToFocus = tabIds[index + 1]; - } else if (index > 0) { - newIdToFocus = tabIds[index - 1]; - } - } - removeTabData(dispatch, TabIdToBeClosed, newIdToFocus); - }; - - const addNewTab = async (where: string) => { - // get a new tabId - const tabId = htmlIdGenerator(TAB_ID_TXT_PFX)(); - - // create a new tab - await initializeTabData(dispatch, tabId, where); - - setTabCreatedTypes((staleState) => { - return { - ...staleState, - [tabId]: where, - }; - }); - - return tabId; - }; - const dispatchSavedObjectId = async () => { - const emptyTabId = getExistingEmptyTab({ + return getExistingEmptyTab({ tabIds: tabIdsRef.current, queries: queryRef.current, explorerData: explorerDataRef.current, }); - const newTabId = emptyTabId ? emptyTabId : await addNewTab(REDIRECT_TAB); - return newTabId; }; useEffect(() => { @@ -150,7 +77,6 @@ export const LogExplorer = ({ if (routerContext && routerContext.searchParams.has(CREATE_TAB_PARAM_KEY)) { // need to wait for current redux event loop to finish setImmediate(() => { - addNewTab(NEW_TAB); routerContext.searchParams.delete(CREATE_TAB_PARAM_KEY); routerContext.routerProps.history.replace({ search: routerContext.searchParams.toString(), @@ -159,78 +85,24 @@ export const LogExplorer = ({ } }, []); - function getQueryTab({ - tabTitle, - tabId, - handlesTabClose, - }: { - tabTitle: string; - tabId: string; - handlesTabClose: (TabIdToBeClosed: string) => void; - }) { - return { - id: tabId, - name: ( - <> - - {tabTitle} - { - e.stopPropagation(); - handlesTabClose(tabId); - }} - data-test-subj="eventExplorer__tabClose" - /> - - - ), - content: ( - <> - - - ), - }; - } - - const memorizedTabs = useMemo(() => { - const res = map(tabIds, (tabId) => { - return getQueryTab({ - tabTitle: tabNames[tabId] || TAB_TITLE, - tabId, - handlesTabClose: handleTabClose, - }); - }); - - return res; - }, [tabIds, tabNames, tabCreatedTypes]); - return ( <> - tab.id === curSelectedTabId)} - onTabClick={(selectedTab: EuiTabbedContentTab) => handleTabClick(selectedTab)} - data-test-subj="eventExplorer__topLevelTabbing" - size="s" + ); diff --git a/public/components/event_analytics/home/__tests__/__snapshots__/saved_query_table.test.tsx.snap b/public/components/event_analytics/home/__tests__/__snapshots__/saved_query_table.test.tsx.snap index fcaaa6c53..c8cb71327 100644 --- a/public/components/event_analytics/home/__tests__/__snapshots__/saved_query_table.test.tsx.snap +++ b/public/components/event_analytics/home/__tests__/__snapshots__/saved_query_table.test.tsx.snap @@ -1081,18 +1081,17 @@ exports[`Saved query table component Renders saved query table 1`] = ` - + @@ -1279,18 +1278,17 @@ exports[`Saved query table component Renders saved query table 1`] = ` - + diff --git a/public/components/event_analytics/home/home.tsx b/public/components/event_analytics/home/home.tsx index e23d242f7..a48064bb7 100644 --- a/public/components/event_analytics/home/home.tsx +++ b/public/components/event_analytics/home/home.tsx @@ -23,7 +23,6 @@ import { EuiSpacer, EuiText, EuiTitle, - htmlIdGenerator, } from '@elastic/eui'; import React, { ReactElement, useEffect, useRef, useState } from 'react'; import { batch, connect, useDispatch } from 'react-redux'; @@ -34,10 +33,8 @@ import { EVENT_ANALYTICS_DOCUMENTATION_URL, NEW_TAB, RAW_QUERY, - REDIRECT_TAB, SELECTED_DATE_RANGE, TAB_CREATED_TYPE, - TAB_ID_TXT_PFX, } from '../../../../common/constants/explorer'; import { EVENT_ANALYTICS, @@ -56,11 +53,9 @@ import { getSampleDataModal } from '../../common/helpers/add_sample_modal'; import { DeleteModal } from '../../common/helpers/delete_modal'; import { onItemSelect, parseGetSuggestions } from '../../common/search/autocomplete_logic'; import { Search } from '../../common/search/search'; -import { init as initFields } from '../redux/slices/field_slice'; -import { init as initPatterns } from '../redux/slices/patterns_slice'; -import { init as initQueryResult, selectQueryResult } from '../redux/slices/query_result_slice'; -import { changeQuery, init as initQuery, selectQueries } from '../redux/slices/query_slice'; -import { addTab, selectQueryTabs, setSelectedQueryTab } from '../redux/slices/query_tab_slice'; +import { selectQueryResult } from '../redux/slices/query_result_slice'; +import { changeQuery, selectQueries } from '../redux/slices/query_slice'; +import { selectQueryTabs, setSelectedQueryTab } from '../redux/slices/query_tab_slice'; import { SavedQueryTable } from './saved_objects_table'; interface IHomeProps { @@ -84,7 +79,6 @@ const EventAnalyticsHome = (props: IHomeProps) => { const { pplService, dslService, - savedObjects, setToast, getExistingEmptyTab, http, @@ -146,22 +140,6 @@ const EventAnalyticsHome = (props: IHomeProps) => { }); }; - const addNewTab = async () => { - // get a new tabId - const tabId = htmlIdGenerator(TAB_ID_TXT_PFX)(); - - // create a new tab - await batch(() => { - dispatch(initQuery({ tabId })); - dispatch(initQueryResult({ tabId })); - dispatch(initFields({ tabId })); - dispatch(addTab({ tabId })); - dispatch(initPatterns({ tabId })); - }); - - return tabId; - }; - useEffect(() => { fetchHistories(); }, []); @@ -188,10 +166,9 @@ const EventAnalyticsHome = (props: IHomeProps) => { queries, explorerData, }); - const newTabId = emptyTabId ? emptyTabId : await addNewTab(); // update this new tab with data - await dispatchInitialData(newTabId); + await dispatchInitialData(emptyTabId); // redirect to explorer history.push('/explorer'); @@ -201,28 +178,6 @@ const EventAnalyticsHome = (props: IHomeProps) => { const handleTimePickerChange = async (timeRange: string[]) => setSelectedDateRange(timeRange); - const handleHistoryClick = async (objectId: string) => { - const emptyTabId = getExistingEmptyTab({ - tabIds: tabsState.queryTabIds, - queries, - explorerData, - }); - const newTabId = emptyTabId ? emptyTabId : await addNewTab(); - batch(() => { - dispatch( - changeQuery({ - tabId: newTabId, - query: { - [TAB_CREATED_TYPE]: REDIRECT_TAB, - }, - }) - ); - dispatch(setSelectedQueryTab({ tabId: newTabId })); - }); - // redirect to explorer - history.push(`/explorer/${objectId}`); - }; - const addSampledata = async () => { setModalLayout( getSampleDataModal(closeModal, async () => { @@ -426,7 +381,6 @@ const EventAnalyticsHome = (props: IHomeProps) => { {savedHistories.length > 0 ? ( { return ( { - handleHistoryClick(item.objectId); - }} + href={`${LOG_EXPLORER_BASE_PATH}${item.objectId}`} data-test-subj="eventHome__savedQueryTableName" > {item.name} diff --git a/public/components/event_analytics/index.tsx b/public/components/event_analytics/index.tsx index 69c469af1..e5714caac 100644 --- a/public/components/event_analytics/index.tsx +++ b/public/components/event_analytics/index.tsx @@ -6,10 +6,8 @@ import { EuiGlobalToastList } from '@elastic/eui'; import { Toast } from '@elastic/eui/src/components/toast/global_toast_list'; import { EmptyTabParams, EventAnalyticsProps } from 'common/types/explorer'; -import { isEmpty } from 'lodash'; import React, { createContext, ReactChild, useState } from 'react'; -import { HashRouter, Route, RouteComponentProps, Switch, useHistory } from 'react-router-dom'; -import { RAW_QUERY } from '../../../common/constants/explorer'; +import { HashRouter, Route, RouteComponentProps, Switch } from 'react-router-dom'; import '../../variables.scss'; import { LogExplorer } from './explorer/log_explorer'; import { Home as EventExplorerHome } from './home/home'; @@ -44,17 +42,7 @@ export const EventAnalytics = ({ setToasts([...toasts, { id: new Date().toISOString(), title, text, color } as Toast]); }; - const getExistingEmptyTab = ({ tabIds, queries, explorerData }: EmptyTabParams) => { - let emptyTabId = ''; - for (let i = 0; i < tabIds!.length; i++) { - const tid = tabIds![i]; - if (isEmpty(queries[tid][RAW_QUERY]) && isEmpty(explorerData[tid])) { - emptyTabId = tid; - break; - } - } - return emptyTabId; - }; + const getExistingEmptyTab = ({ tabIds }: EmptyTabParams) => tabIds[0]; return ( <> diff --git a/public/framework/redux/store/shared_state.ts b/public/framework/redux/store/shared_state.ts index ee041c9db..b073d7348 100644 --- a/public/framework/redux/store/shared_state.ts +++ b/public/framework/redux/store/shared_state.ts @@ -3,7 +3,4 @@ * SPDX-License-Identifier: Apache-2.0 */ -import { htmlIdGenerator } from '@elastic/eui'; -import { TAB_ID_TXT_PFX } from '../../../../common/constants/explorer'; - -export const initialTabId: string = htmlIdGenerator(TAB_ID_TXT_PFX)(); +export const initialTabId: string = 'OBSERVABILITY_DEFAULT_TAB';