diff --git a/frontend/src/container/GridTableComponent/__tests__/utils.test.tsx b/frontend/src/container/GridTableComponent/__tests__/utils.test.tsx index f0582a51fb..e8f7a631bd 100644 --- a/frontend/src/container/GridTableComponent/__tests__/utils.test.tsx +++ b/frontend/src/container/GridTableComponent/__tests__/utils.test.tsx @@ -1,6 +1,10 @@ import { Query } from 'types/api/queryBuilder/queryBuilderData'; -import { createColumnsAndDataSource, getQueryLegend } from '../utils'; +import { + createColumnsAndDataSource, + getQueryLegend, + sortFunction, +} from '../utils'; import { expectedOutputWithLegends, tableDataMultipleQueriesSuccessResponse, @@ -39,4 +43,88 @@ describe('Table Panel utils', () => { // should return undefined when legend not present expect(getQueryLegend(query, 'B')).toBe(undefined); }); + + it('sorter function for table sorting', () => { + let rowA: { + A: string | number; + timestamp: number; + key: string; + } = { + A: 22.4, + timestamp: 111111, + key: '1111', + }; + let rowB: { + A: string | number; + timestamp: number; + key: string; + } = { + A: 'n/a', + timestamp: 111112, + key: '1112', + }; + const item = { + isValueColumn: true, + name: 'A', + queryName: 'A', + }; + // A has value and value is considered bigger than n/a hence 1 + expect(sortFunction(rowA, rowB, item)).toBe(1); + + rowA = { + A: 'n/a', + timestamp: 111111, + key: '1111', + }; + rowB = { + A: 22.4, + timestamp: 111112, + key: '1112', + }; + + // B has value and value is considered bigger than n/a hence -1 + expect(sortFunction(rowA, rowB, item)).toBe(-1); + + rowA = { + A: 11, + timestamp: 111111, + key: '1111', + }; + rowB = { + A: 22, + timestamp: 111112, + key: '1112', + }; + + // A and B has value , since B > A hence A-B + expect(sortFunction(rowA, rowB, item)).toBe(-11); + + rowA = { + A: 'read', + timestamp: 111111, + key: '1111', + }; + rowB = { + A: 'write', + timestamp: 111112, + key: '1112', + }; + + // A and B are strings so A is smaller than B because r comes before w hence -1 + expect(sortFunction(rowA, rowB, item)).toBe(-1); + + rowA = { + A: 'n/a', + timestamp: 111111, + key: '1111', + }; + rowB = { + A: 'n/a', + timestamp: 111112, + key: '1112', + }; + + // A and B are strings n/a , since both of them are same hence 0 + expect(sortFunction(rowA, rowB, item)).toBe(0); + }); }); diff --git a/frontend/src/container/GridTableComponent/utils.ts b/frontend/src/container/GridTableComponent/utils.ts index 089a35fe00..acd58af62d 100644 --- a/frontend/src/container/GridTableComponent/utils.ts +++ b/frontend/src/container/GridTableComponent/utils.ts @@ -1,3 +1,4 @@ +/* eslint-disable sonarjs/cognitive-complexity */ import { ColumnsType, ColumnType } from 'antd/es/table'; import { ThresholdProps } from 'container/NewWidget/RightContainer/Threshold/types'; import { QUERY_TABLE_CONFIG } from 'container/QueryTable/config'; @@ -105,6 +106,39 @@ export function getQueryLegend( return legend; } +export function sortFunction( + a: RowData, + b: RowData, + item: { + name: string; + queryName: string; + isValueColumn: boolean; + }, +): number { + // assumption :- number values is bigger than 'n/a' + const valueA = Number(a[`${item.name}_without_unit`] ?? a[item.name]); + const valueB = Number(b[`${item.name}_without_unit`] ?? b[item.name]); + + // if both the values are numbers then return the difference here + if (!isNaN(valueA) && !isNaN(valueB)) { + return valueA - valueB; + } + + // if valueB is a number then make it bigger value + if (isNaN(valueA) && !isNaN(valueB)) { + return -1; + } + + // if valueA is number make it the bigger value + if (!isNaN(valueA) && isNaN(valueB)) { + return 1; + } + + // if both of them are strings do the localecompare + return ((a[item.name] as string) || '').localeCompare( + (b[item.name] as string) || '', + ); +} export function createColumnsAndDataSource( data: TableData, currentQuery: Query, @@ -123,18 +157,7 @@ export function createColumnsAndDataSource( title: !isEmpty(legend) ? legend : item.name, width: QUERY_TABLE_CONFIG.width, render: renderColumnCell && renderColumnCell[item.name], - sorter: (a: RowData, b: RowData): number => { - const valueA = Number(a[`${item.name}_without_unit`] ?? a[item.name]); - const valueB = Number(b[`${item.name}_without_unit`] ?? b[item.name]); - - if (!isNaN(valueA) && !isNaN(valueB)) { - return valueA - valueB; - } - - return ((a[item.name] as string) || '').localeCompare( - (b[item.name] as string) || '', - ); - }, + sorter: (a: RowData, b: RowData): number => sortFunction(a, b, item), }; return [...acc, column];