From ddf5569ce91264a52a86dcc1c38ca9fe99ea21e4 Mon Sep 17 00:00:00 2001 From: SagarRajput-7 <162284829+SagarRajput-7@users.noreply.github.com> Date: Wed, 10 Jul 2024 11:56:11 +0530 Subject: [PATCH] fix: added null check on filters obj (#5419) * fix: added null check on filters obj * feat: added test cases of undefined filters and items * feat: added comments --- .../pages/TracesExplorer/Filter/Filter.tsx | 2 +- .../__test__/TracesExplorer.test.tsx | 132 ++++++++++++++++++ 2 files changed, 133 insertions(+), 1 deletion(-) create mode 100644 frontend/src/pages/TracesExplorer/__test__/TracesExplorer.test.tsx diff --git a/frontend/src/pages/TracesExplorer/Filter/Filter.tsx b/frontend/src/pages/TracesExplorer/Filter/Filter.tsx index 7eadc3d5cd..1a3fbc785c 100644 --- a/frontend/src/pages/TracesExplorer/Filter/Filter.tsx +++ b/frontend/src/pages/TracesExplorer/Filter/Filter.tsx @@ -56,7 +56,7 @@ export function Filter(props: FilterProps): JSX.Element { return {} as FilterType; } - return filters.items + return (filters.items || []) .filter((item) => Object.keys(AllTraceFilterKeyValue).includes(item.key?.key as string), ) diff --git a/frontend/src/pages/TracesExplorer/__test__/TracesExplorer.test.tsx b/frontend/src/pages/TracesExplorer/__test__/TracesExplorer.test.tsx new file mode 100644 index 0000000000..1250a3f3cc --- /dev/null +++ b/frontend/src/pages/TracesExplorer/__test__/TracesExplorer.test.tsx @@ -0,0 +1,132 @@ +/* eslint-disable sonarjs/no-duplicate-string */ +/* eslint-disable no-restricted-syntax */ +/* eslint-disable no-await-in-loop */ +import { + initialQueriesMap, + initialQueryBuilderFormValues, +} from 'constants/queryBuilder'; +import ROUTES from 'constants/routes'; +import * as compositeQueryHook from 'hooks/queryBuilder/useGetCompositeQueryParam'; +import { render } from 'tests/test-utils'; +import { DataTypes } from 'types/api/queryBuilder/queryAutocompleteResponse'; +import { Query } from 'types/api/queryBuilder/queryBuilderData'; + +import { Filter } from '../Filter/Filter'; +import { AllTraceFilterKeyValue } from '../Filter/filterUtils'; + +jest.mock('react-router-dom', () => ({ + ...jest.requireActual('react-router-dom'), + useLocation: (): { pathname: string } => ({ + pathname: `${process.env.FRONTEND_API_ENDPOINT}${ROUTES.TRACES_EXPLORER}/`, + }), +})); + +jest.mock('uplot', () => { + const paths = { + spline: jest.fn(), + bars: jest.fn(), + }; + + const uplotMock = jest.fn(() => ({ + paths, + })); + + return { + paths, + default: uplotMock, + }; +}); + +const compositeQuery: Query = { + ...initialQueriesMap.traces, + builder: { + ...initialQueriesMap.traces.builder, + queryData: [ + { + ...initialQueryBuilderFormValues, + filters: { + items: [ + { + id: '95564eb1', + key: { + key: 'name', + dataType: DataTypes.String, + type: 'tag', + isColumn: true, + isJSON: false, + id: 'name--string--tag--true', + }, + op: 'in', + value: ['HTTP GET /customer'], + }, + { + id: '3337951c', + key: { + key: 'serviceName', + dataType: DataTypes.String, + type: 'tag', + isColumn: true, + isJSON: false, + id: 'serviceName--string--tag--true', + }, + op: 'in', + value: ['demo-app'], + }, + ], + op: 'AND', + }, + }, + ], + }, +}; + +describe('TracesExplorer - ', () => { + it('test edge cases of undefined filters', async () => { + jest.spyOn(compositeQueryHook, 'useGetCompositeQueryParam').mockReturnValue({ + ...compositeQuery, + builder: { + ...compositeQuery.builder, + queryData: compositeQuery.builder.queryData.map( + (item) => + ({ + ...item, + filters: undefined, + } as any), + ), + }, + }); + + const { getByText } = render(); + + // we should have all the filters + Object.values(AllTraceFilterKeyValue).forEach((filter) => { + expect(getByText(filter)).toBeInTheDocument(); + }); + }); + + it('test edge cases of undefined filters - items', async () => { + jest.spyOn(compositeQueryHook, 'useGetCompositeQueryParam').mockReturnValue({ + ...compositeQuery, + builder: { + ...compositeQuery.builder, + queryData: compositeQuery.builder.queryData.map( + (item) => + ({ + ...item, + filters: { + ...item.filters, + items: undefined, + }, + } as any), + ), + }, + }); + + const { getByText } = render(); + + // we should have all the filters + Object.values(AllTraceFilterKeyValue).forEach((filter) => { + expect(getByText(filter)).toBeInTheDocument(); + }); + }); +});