mirror of
https://github.com/SigNoz/signoz.git
synced 2026-04-28 06:30:33 +01:00
Compare commits
1 Commits
cancel-sub
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
500ce85ccb |
@@ -212,9 +212,9 @@
|
||||
"msw": "1.3.2",
|
||||
"npm-run-all": "latest",
|
||||
"orval": "7.18.0",
|
||||
"oxfmt": "0.46.0",
|
||||
"oxlint": "1.61.0",
|
||||
"oxlint-tsgolint": "0.21.1",
|
||||
"oxfmt": "0.47.0",
|
||||
"oxlint": "1.62.0",
|
||||
"oxlint-tsgolint": "0.22.1",
|
||||
"portfinder-sync": "^0.0.2",
|
||||
"postcss": "8.5.6",
|
||||
"postcss-scss": "4.0.9",
|
||||
@@ -238,9 +238,12 @@
|
||||
},
|
||||
"lint-staged": {
|
||||
"*.(js|jsx|ts|tsx)": [
|
||||
"oxfmt --check",
|
||||
"oxlint --quiet",
|
||||
"oxlint --fix",
|
||||
"oxfmt --write",
|
||||
"sh scripts/typecheck-staged.sh"
|
||||
],
|
||||
"*.(scss|css)": [
|
||||
"stylelint"
|
||||
]
|
||||
},
|
||||
"resolutions": {
|
||||
|
||||
@@ -105,7 +105,7 @@ function createMockLicense(
|
||||
status: '',
|
||||
updated_at: '0',
|
||||
},
|
||||
state: LicenseState.ACTIVATED,
|
||||
state: LicenseState.ACTIVE,
|
||||
status: LicenseStatus.VALID,
|
||||
platform: LicensePlatform.CLOUD,
|
||||
created_at: '0',
|
||||
@@ -931,7 +931,7 @@ describe('PrivateRoute', () => {
|
||||
isFetchingActiveLicense: false,
|
||||
activeLicense: createMockLicense({
|
||||
platform: LicensePlatform.CLOUD,
|
||||
state: LicenseState.ACTIVATED,
|
||||
state: LicenseState.ACTIVE,
|
||||
}),
|
||||
},
|
||||
isCloudUser: true,
|
||||
@@ -1522,7 +1522,7 @@ describe('PrivateRoute', () => {
|
||||
isFetchingActiveLicense: false,
|
||||
activeLicense: createMockLicense({
|
||||
platform: LicensePlatform.CLOUD,
|
||||
state: LicenseState.ACTIVATED,
|
||||
state: LicenseState.ACTIVE,
|
||||
}),
|
||||
trialInfo: createMockTrialInfo({ workSpaceBlock: false }),
|
||||
user: createMockUser({ role: USER_ROLES.ADMIN as ROLES }),
|
||||
|
||||
@@ -104,7 +104,7 @@ describe('getFieldKeys API', () => {
|
||||
const result = await getFieldKeys('traces');
|
||||
|
||||
// Verify the returned structure matches SuccessResponseV2 format
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
httpStatusCode: 200,
|
||||
data: mockSuccessResponse.data.data,
|
||||
});
|
||||
|
||||
@@ -199,7 +199,7 @@ describe('getFieldValues API', () => {
|
||||
const result = await getFieldValues('traces', 'service.name');
|
||||
|
||||
// Verify the returned structure matches SuccessResponseV2 format
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
httpStatusCode: 200,
|
||||
data: expect.objectContaining({
|
||||
values: expect.any(Object),
|
||||
|
||||
@@ -76,10 +76,10 @@ describe('interceptorRejected', () => {
|
||||
}
|
||||
|
||||
const mockAxiosFn = axios as unknown as jest.Mock;
|
||||
expect(mockAxiosFn.mock.calls.length).toBe(1);
|
||||
expect(mockAxiosFn.mock.calls).toHaveLength(1);
|
||||
const retryCallConfig = mockAxiosFn.mock.calls[0][0];
|
||||
expect(Array.isArray(JSON.parse(retryCallConfig.data))).toBe(true);
|
||||
expect(JSON.parse(retryCallConfig.data)).toEqual(arrayPayload);
|
||||
expect(JSON.parse(retryCallConfig.data)).toStrictEqual(arrayPayload);
|
||||
});
|
||||
|
||||
it('should preserve object payload structure when retrying a 401 request', async () => {
|
||||
@@ -112,9 +112,9 @@ describe('interceptorRejected', () => {
|
||||
}
|
||||
|
||||
const mockAxiosFn = axios as unknown as jest.Mock;
|
||||
expect(mockAxiosFn.mock.calls.length).toBe(1);
|
||||
expect(mockAxiosFn.mock.calls).toHaveLength(1);
|
||||
const retryCallConfig = mockAxiosFn.mock.calls[0][0];
|
||||
expect(JSON.parse(retryCallConfig.data)).toEqual(objectPayload);
|
||||
expect(JSON.parse(retryCallConfig.data)).toStrictEqual(objectPayload);
|
||||
});
|
||||
|
||||
it('should handle undefined data gracefully when retrying', async () => {
|
||||
@@ -145,7 +145,7 @@ describe('interceptorRejected', () => {
|
||||
}
|
||||
|
||||
const mockAxiosFn = axios as unknown as jest.Mock;
|
||||
expect(mockAxiosFn.mock.calls.length).toBe(1);
|
||||
expect(mockAxiosFn.mock.calls).toHaveLength(1);
|
||||
const retryCallConfig = mockAxiosFn.mock.calls[0][0];
|
||||
expect(retryCallConfig.data).toBeUndefined();
|
||||
});
|
||||
|
||||
@@ -99,7 +99,7 @@ describe('convertV5ResponseToLegacy', () => {
|
||||
const q = result.payload.data.result[0];
|
||||
expect(q.queryName).toBe('A');
|
||||
expect(q.legend).toBe('{{service.name}}');
|
||||
expect(q.series?.[0]).toEqual(
|
||||
expect(q.series?.[0]).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
labels: { 'service.name': 'adservice' },
|
||||
values: [
|
||||
@@ -186,7 +186,7 @@ describe('convertV5ResponseToLegacy', () => {
|
||||
|
||||
expect(result.payload.data.resultType).toBe('scalar');
|
||||
const [tableEntry] = result.payload.data.result;
|
||||
expect(tableEntry.table?.columns).toEqual([
|
||||
expect(tableEntry.table?.columns).toStrictEqual([
|
||||
{
|
||||
name: 'service.name',
|
||||
queryName: 'A',
|
||||
@@ -202,7 +202,7 @@ describe('convertV5ResponseToLegacy', () => {
|
||||
},
|
||||
{ name: 'F1', queryName: 'F1', isValueColumn: true, id: 'F1' },
|
||||
]);
|
||||
expect(tableEntry.table?.rows?.[0]).toEqual({
|
||||
expect(tableEntry.table?.rows?.[0]).toStrictEqual({
|
||||
data: {
|
||||
'service.name': 'adservice',
|
||||
'A.count()': 606,
|
||||
@@ -257,7 +257,7 @@ describe('convertV5ResponseToLegacy', () => {
|
||||
|
||||
expect(result.payload.data.resultType).toBe('scalar');
|
||||
const [tableEntry] = result.payload.data.result;
|
||||
expect(tableEntry.table?.columns).toEqual([
|
||||
expect(tableEntry.table?.columns).toStrictEqual([
|
||||
{
|
||||
name: 'service.name',
|
||||
queryName: 'A',
|
||||
@@ -267,7 +267,7 @@ describe('convertV5ResponseToLegacy', () => {
|
||||
// Single aggregation: name resolves to legend, id resolves to queryName
|
||||
{ name: '{{service.name}}', queryName: 'A', isValueColumn: true, id: 'A' },
|
||||
]);
|
||||
expect(tableEntry.table?.rows?.[0]).toEqual({
|
||||
expect(tableEntry.table?.rows?.[0]).toStrictEqual({
|
||||
data: {
|
||||
'service.name': 'adservice',
|
||||
A: 580,
|
||||
|
||||
@@ -104,7 +104,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { A: 'Legend A', F1: 'Formula Legend' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -154,7 +154,10 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
);
|
||||
|
||||
// Legend map combines builder and formulas
|
||||
expect(result.legendMap).toEqual({ A: 'Legend A', F1: 'Formula Legend' });
|
||||
expect(result.legendMap).toStrictEqual({
|
||||
A: 'Legend A',
|
||||
F1: 'Formula Legend',
|
||||
});
|
||||
|
||||
const payload: QueryRangePayloadV5 = result.queryPayload;
|
||||
|
||||
@@ -166,10 +169,10 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
expect(payload.formatOptions?.fillGaps).toBe(true);
|
||||
|
||||
// Variables mapped as { key: { value } }
|
||||
expect(payload.variables).toEqual({
|
||||
svc: { value: 'api' },
|
||||
count: { value: 5 },
|
||||
flag: { value: true },
|
||||
expect(payload.variables).toStrictEqual({
|
||||
svc: { value: 'api', type: undefined },
|
||||
count: { value: 5, type: undefined },
|
||||
flag: { value: true, type: undefined },
|
||||
});
|
||||
|
||||
// Queries include one builder_query and one builder_formula
|
||||
@@ -226,7 +229,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { A: 'LP' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -255,7 +258,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
}),
|
||||
);
|
||||
|
||||
expect(result.legendMap).toEqual({ A: 'LP' });
|
||||
expect(result.legendMap).toStrictEqual({ A: 'LP' });
|
||||
|
||||
const payload: QueryRangePayloadV5 = result.queryPayload;
|
||||
expect(payload.requestType).toBe('time_series');
|
||||
@@ -296,7 +299,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { Q: 'LC' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -324,7 +327,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
}),
|
||||
);
|
||||
|
||||
expect(result.legendMap).toEqual({ Q: 'LC' });
|
||||
expect(result.legendMap).toStrictEqual({ Q: 'LC' });
|
||||
|
||||
const payload: QueryRangePayloadV5 = result.queryPayload;
|
||||
expect(payload.requestType).toBe('scalar');
|
||||
@@ -353,7 +356,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: {},
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -397,7 +400,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { A: 'Legend A' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -471,7 +474,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { A: 'Legend A' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -585,7 +588,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result).toEqual(
|
||||
expect(result).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
legendMap: { A: '{{service.name}}' },
|
||||
queryPayload: expect.objectContaining({
|
||||
@@ -684,7 +687,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
const result = prepareQueryRangePayloadV5(props);
|
||||
|
||||
expect(result.legendMap).toEqual({ A: 'Legend A' });
|
||||
expect(result.legendMap).toStrictEqual({ A: 'Legend A' });
|
||||
expect(result.queryPayload.compositeQuery.queries).toHaveLength(1);
|
||||
|
||||
const builderQuery = result.queryPayload.compositeQuery.queries.find(
|
||||
@@ -694,7 +697,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
|
||||
expect(logSpec.name).toBe('A');
|
||||
expect(logSpec.signal).toBe('logs');
|
||||
expect(logSpec.filter).toEqual({
|
||||
expect(logSpec.filter).toStrictEqual({
|
||||
expression:
|
||||
"service.name = 'payment-service' AND http.status_code >= 400 AND message contains 'error'",
|
||||
});
|
||||
@@ -731,7 +734,9 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
(q) => q.type === 'builder_query',
|
||||
) as QueryEnvelope;
|
||||
const logSpec = builderQuery.spec as LogBuilderQuery;
|
||||
expect(logSpec.filter).toEqual({ expression: 'http.status_code >= 500' });
|
||||
expect(logSpec.filter).toStrictEqual({
|
||||
expression: 'http.status_code >= 500',
|
||||
});
|
||||
});
|
||||
|
||||
it('derives expression from filters when filter is undefined', () => {
|
||||
@@ -775,7 +780,9 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
(q) => q.type === 'builder_query',
|
||||
) as QueryEnvelope;
|
||||
const logSpec = builderQuery.spec as LogBuilderQuery;
|
||||
expect(logSpec.filter).toEqual({ expression: "service.name = 'checkout'" });
|
||||
expect(logSpec.filter).toStrictEqual({
|
||||
expression: "service.name = 'checkout'",
|
||||
});
|
||||
});
|
||||
|
||||
it('prefers filter.expression over filters when both are present', () => {
|
||||
@@ -819,7 +826,9 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
(q) => q.type === 'builder_query',
|
||||
) as QueryEnvelope;
|
||||
const logSpec = builderQuery.spec as LogBuilderQuery;
|
||||
expect(logSpec.filter).toEqual({ expression: "service.name = 'frontend'" });
|
||||
expect(logSpec.filter).toStrictEqual({
|
||||
expression: "service.name = 'frontend'",
|
||||
});
|
||||
});
|
||||
|
||||
it('returns empty expression when neither filter nor filters provided', () => {
|
||||
@@ -853,7 +862,7 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
(q) => q.type === 'builder_query',
|
||||
) as QueryEnvelope;
|
||||
const logSpec = builderQuery.spec as LogBuilderQuery;
|
||||
expect(logSpec.filter).toEqual({ expression: '' });
|
||||
expect(logSpec.filter).toStrictEqual({ expression: '' });
|
||||
});
|
||||
|
||||
it('returns empty expression when filters provided with empty items', () => {
|
||||
@@ -887,6 +896,6 @@ describe('prepareQueryRangePayloadV5', () => {
|
||||
(q) => q.type === 'builder_query',
|
||||
) as QueryEnvelope;
|
||||
const logSpec = builderQuery.spec as LogBuilderQuery;
|
||||
expect(logSpec.filter).toEqual({ expression: '' });
|
||||
expect(logSpec.filter).toStrictEqual({ expression: '' });
|
||||
});
|
||||
});
|
||||
|
||||
@@ -213,7 +213,7 @@ describe.each([
|
||||
const callArgs = mockDownloadExportData.mock.calls[0][0];
|
||||
const query = callArgs.body.compositeQuery.queries[0];
|
||||
expect(query.spec.groupBy).toBeUndefined();
|
||||
expect(query.spec.having).toEqual({ expression: '' });
|
||||
expect(query.spec.having).toStrictEqual({ expression: '' });
|
||||
});
|
||||
});
|
||||
|
||||
@@ -238,7 +238,7 @@ describe.each([
|
||||
expect(mockDownloadExportData).toHaveBeenCalledTimes(1);
|
||||
const callArgs = mockDownloadExportData.mock.calls[0][0];
|
||||
const query = callArgs.body.compositeQuery.queries[0];
|
||||
expect(query.spec.selectFields).toEqual([
|
||||
expect(query.spec.selectFields).toStrictEqual([
|
||||
expect.objectContaining({
|
||||
name: 'http.status',
|
||||
fieldDataType: 'int64',
|
||||
|
||||
@@ -6,39 +6,39 @@ jest.mock('react-dnd', () => ({
|
||||
}));
|
||||
|
||||
describe('Utils testing of DraggableTableRow component', () => {
|
||||
test('Should dropHandler return true', () => {
|
||||
it('Should dropHandler return true', () => {
|
||||
const monitor = {
|
||||
isOver: jest.fn().mockReturnValueOnce(true),
|
||||
} as never;
|
||||
const dropDataTruthy = dropHandler(monitor);
|
||||
|
||||
expect(dropDataTruthy).toEqual({ isOver: true });
|
||||
expect(dropDataTruthy).toStrictEqual({ isOver: true });
|
||||
});
|
||||
|
||||
test('Should dropHandler return false', () => {
|
||||
it('Should dropHandler return false', () => {
|
||||
const monitor = {
|
||||
isOver: jest.fn().mockReturnValueOnce(false),
|
||||
} as never;
|
||||
const dropDataFalsy = dropHandler(monitor);
|
||||
|
||||
expect(dropDataFalsy).toEqual({ isOver: false });
|
||||
expect(dropDataFalsy).toStrictEqual({ isOver: false });
|
||||
});
|
||||
|
||||
test('Should dragHandler return true', () => {
|
||||
it('Should dragHandler return true', () => {
|
||||
const monitor = {
|
||||
isDragging: jest.fn().mockReturnValueOnce(true),
|
||||
} as never;
|
||||
const dragDataTruthy = dragHandler(monitor);
|
||||
|
||||
expect(dragDataTruthy).toEqual({ isDragging: true });
|
||||
expect(dragDataTruthy).toStrictEqual({ isDragging: true });
|
||||
});
|
||||
|
||||
test('Should dragHandler return false', () => {
|
||||
it('Should dragHandler return false', () => {
|
||||
const monitor = {
|
||||
isDragging: jest.fn().mockReturnValueOnce(false),
|
||||
} as never;
|
||||
const dragDataFalsy = dragHandler(monitor);
|
||||
|
||||
expect(dragDataFalsy).toEqual({ isDragging: false });
|
||||
expect(dragDataFalsy).toStrictEqual({ isDragging: false });
|
||||
});
|
||||
});
|
||||
|
||||
@@ -361,9 +361,9 @@ describe('EditMemberDrawer', () => {
|
||||
|
||||
await user.click(screen.getByRole('button', { name: /delete member/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByText(/are you sure you want to delete/i),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/are you sure you want to delete/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const confirmBtns = screen.getAllByRole('button', { name: /delete member/i });
|
||||
await user.click(confirmBtns[confirmBtns.length - 1]);
|
||||
@@ -441,9 +441,9 @@ describe('EditMemberDrawer', () => {
|
||||
|
||||
await user.click(screen.getByRole('button', { name: /revoke invite/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByText(/Are you sure you want to revoke the invite/i),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/Are you sure you want to revoke the invite/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const confirmBtns = screen.getAllByRole('button', { name: /revoke invite/i });
|
||||
await user.click(confirmBtns[confirmBtns.length - 1]);
|
||||
|
||||
@@ -64,7 +64,7 @@ export const legend = (id: string, isLonger: boolean): Plugin<ChartType> => ({
|
||||
// li.style.marginTop = '5px';
|
||||
|
||||
li.onclick = (): void => {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
const { type } = chart.config;
|
||||
if (type === 'pie' || type === 'doughnut') {
|
||||
// Pie and doughnut charts only have a single dataset and visibility is per item
|
||||
|
||||
@@ -9,65 +9,65 @@ describe('xAxisConfig for Chart', () => {
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'millisecond');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.millisecond,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.millisecond);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'second');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.second,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.second);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'minute');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.minute,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.minute);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'hour');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.hour,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.hour);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'day');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.day,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.day);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'week');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.week,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.week);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'month');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.month,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.month);
|
||||
}
|
||||
{
|
||||
const start = dayjs();
|
||||
const end = start.add(10, 'year');
|
||||
|
||||
expect(convertTimeRange(start.valueOf(), end.valueOf()).unitName).toEqual(
|
||||
TIME_UNITS.year,
|
||||
);
|
||||
expect(
|
||||
convertTimeRange(start.valueOf(), end.valueOf()).unitName,
|
||||
).toStrictEqual(TIME_UNITS.year);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
@@ -7,7 +7,7 @@ const testFullPrecisionGetYAxisFormattedValue = (
|
||||
): string => getYAxisFormattedValue(value, format, PrecisionOptionsEnum.FULL);
|
||||
|
||||
describe('getYAxisFormattedValue - none (full precision legacy assertions)', () => {
|
||||
test('large integers and decimals', () => {
|
||||
it('large integers and decimals', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('250034', 'none')).toBe(
|
||||
'250034',
|
||||
);
|
||||
@@ -22,7 +22,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('preserves leading zeros after decimal until first non-zero', () => {
|
||||
it('preserves leading zeros after decimal until first non-zero', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1.0000234', 'none')).toBe(
|
||||
'1.0000234',
|
||||
);
|
||||
@@ -31,7 +31,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('trims to three significant decimals and removes trailing zeros', () => {
|
||||
it('trims to three significant decimals and removes trailing zeros', () => {
|
||||
expect(
|
||||
testFullPrecisionGetYAxisFormattedValue('0.000000250034', 'none'),
|
||||
).toBe('0.000000250034');
|
||||
@@ -55,7 +55,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
).toBe('0.00000025');
|
||||
});
|
||||
|
||||
test('whole numbers normalize', () => {
|
||||
it('whole numbers normalize', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1000', 'none')).toBe('1000');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('99.5458', 'none')).toBe(
|
||||
'99.5458',
|
||||
@@ -68,7 +68,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('strip redundant decimal zeros', () => {
|
||||
it('strip redundant decimal zeros', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1000.000', 'none')).toBe(
|
||||
'1000',
|
||||
);
|
||||
@@ -78,7 +78,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1.000', 'none')).toBe('1');
|
||||
});
|
||||
|
||||
test('edge values', () => {
|
||||
it('edge values', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0', 'none')).toBe('0');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('-0', 'none')).toBe('0');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('Infinity', 'none')).toBe('∞');
|
||||
@@ -92,7 +92,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('abc123', 'none')).toBe('NaN');
|
||||
});
|
||||
|
||||
test('small decimals keep precision as-is', () => {
|
||||
it('small decimals keep precision as-is', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.0001', 'none')).toBe(
|
||||
'0.0001',
|
||||
);
|
||||
@@ -104,7 +104,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('simple decimals preserved', () => {
|
||||
it('simple decimals preserved', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.1', 'none')).toBe('0.1');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.2', 'none')).toBe('0.2');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.3', 'none')).toBe('0.3');
|
||||
@@ -115,7 +115,7 @@ describe('getYAxisFormattedValue - none (full precision legacy assertions)', ()
|
||||
});
|
||||
|
||||
describe('getYAxisFormattedValue - units (full precision legacy assertions)', () => {
|
||||
test('ms', () => {
|
||||
it('ms', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1500', 'ms')).toBe('1.5 s');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('500', 'ms')).toBe('500 ms');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('60000', 'ms')).toBe('1 min');
|
||||
@@ -127,19 +127,19 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('s', () => {
|
||||
it('s', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('90', 's')).toBe('1.5 mins');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('30', 's')).toBe('30 s');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('3600', 's')).toBe('1 hour');
|
||||
});
|
||||
|
||||
test('m', () => {
|
||||
it('m', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('90', 'm')).toBe('1.5 hours');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('30', 'm')).toBe('30 min');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1440', 'm')).toBe('1 day');
|
||||
});
|
||||
|
||||
test('bytes', () => {
|
||||
it('bytes', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1024', 'bytes')).toBe(
|
||||
'1 KiB',
|
||||
);
|
||||
@@ -149,7 +149,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('mbytes', () => {
|
||||
it('mbytes', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1024', 'mbytes')).toBe(
|
||||
'1 GiB',
|
||||
);
|
||||
@@ -161,7 +161,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('kbytes', () => {
|
||||
it('kbytes', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1024', 'kbytes')).toBe(
|
||||
'1 MiB',
|
||||
);
|
||||
@@ -173,7 +173,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('short', () => {
|
||||
it('short', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1000', 'short')).toBe('1 K');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('1500', 'short')).toBe(
|
||||
'1.5 K',
|
||||
@@ -201,7 +201,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('percent', () => {
|
||||
it('percent', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.15', 'percent')).toBe(
|
||||
'0.15%',
|
||||
);
|
||||
@@ -235,7 +235,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
).toBe('1.005555555595959%');
|
||||
});
|
||||
|
||||
test('ratio', () => {
|
||||
it('ratio', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0.5', 'ratio')).toBe(
|
||||
'0.5 ratio',
|
||||
);
|
||||
@@ -247,7 +247,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('temperature units', () => {
|
||||
it('temperature units', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('25', 'celsius')).toBe(
|
||||
'25 °C',
|
||||
);
|
||||
@@ -267,13 +267,13 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
);
|
||||
});
|
||||
|
||||
test('ms edge cases', () => {
|
||||
it('ms edge cases', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0', 'ms')).toBe('0 ms');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('-1500', 'ms')).toBe('-1.5 s');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('Infinity', 'ms')).toBe('∞');
|
||||
});
|
||||
|
||||
test('bytes edge cases', () => {
|
||||
it('bytes edge cases', () => {
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('0', 'bytes')).toBe('0 B');
|
||||
expect(testFullPrecisionGetYAxisFormattedValue('-1024', 'bytes')).toBe(
|
||||
'-1 KiB',
|
||||
@@ -282,7 +282,7 @@ describe('getYAxisFormattedValue - units (full precision legacy assertions)', ()
|
||||
});
|
||||
|
||||
describe('getYAxisFormattedValue - precision option tests', () => {
|
||||
test('precision 0 drops decimal part', () => {
|
||||
it('precision 0 drops decimal part', () => {
|
||||
expect(getYAxisFormattedValue('1.2345', 'none', 0)).toBe('1');
|
||||
expect(getYAxisFormattedValue('0.9999', 'none', 0)).toBe('0');
|
||||
expect(getYAxisFormattedValue('12345.6789', 'none', 0)).toBe('12345');
|
||||
@@ -294,7 +294,7 @@ describe('getYAxisFormattedValue - precision option tests', () => {
|
||||
// with unit
|
||||
expect(getYAxisFormattedValue('4353.81', 'ms', 0)).toBe('4 s');
|
||||
});
|
||||
test('precision 1,2,3,4 decimals', () => {
|
||||
it('precision 1,2,3,4 decimals', () => {
|
||||
expect(getYAxisFormattedValue('1.2345', 'none', 1)).toBe('1.2');
|
||||
expect(getYAxisFormattedValue('1.2345', 'none', 2)).toBe('1.23');
|
||||
expect(getYAxisFormattedValue('1.2345', 'none', 3)).toBe('1.234');
|
||||
@@ -345,7 +345,7 @@ describe('getYAxisFormattedValue - precision option tests', () => {
|
||||
expect(getYAxisFormattedValue('0.123456', 'percent', 4)).toBe('0.1235%'); // approximation
|
||||
});
|
||||
|
||||
test('precision full uses up to DEFAULT_SIGNIFICANT_DIGITS significant digits', () => {
|
||||
it('precision full uses up to DEFAULT_SIGNIFICANT_DIGITS significant digits', () => {
|
||||
expect(
|
||||
getYAxisFormattedValue(
|
||||
'0.00002625429914148441',
|
||||
|
||||
@@ -90,11 +90,11 @@ describe('InviteMembersModal', () => {
|
||||
screen.getByRole('button', { name: /invite team members/i }),
|
||||
);
|
||||
|
||||
expect(
|
||||
await screen.findByText(
|
||||
await expect(
|
||||
screen.findByText(
|
||||
'Please enter valid emails and select roles for team members',
|
||||
),
|
||||
).toBeInTheDocument();
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('shows email-only message when email is invalid but role is selected', async () => {
|
||||
@@ -112,9 +112,9 @@ describe('InviteMembersModal', () => {
|
||||
screen.getByRole('button', { name: /invite team members/i }),
|
||||
);
|
||||
|
||||
expect(
|
||||
await screen.findByText('Please enter valid emails for team members'),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('Please enter valid emails for team members'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('shows role-only message when email is valid but role is missing', async () => {
|
||||
@@ -130,9 +130,9 @@ describe('InviteMembersModal', () => {
|
||||
screen.getByRole('button', { name: /invite team members/i }),
|
||||
);
|
||||
|
||||
expect(
|
||||
await screen.findByText('Please select roles for team members'),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('Please select roles for team members'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -27,7 +27,7 @@ describe('getLogIndicatorType', () => {
|
||||
expect(getLogIndicatorType(log)).toBe('TRACE');
|
||||
});
|
||||
|
||||
it('severity_text should be used when severity_number is absent ', () => {
|
||||
it('severity_text should be used when severity_number is absent', () => {
|
||||
const log = {
|
||||
date: '2024-02-29T12:34:46Z',
|
||||
timestamp: 1646115296,
|
||||
|
||||
@@ -75,7 +75,7 @@ function OptionsMenu({
|
||||
};
|
||||
|
||||
const handleSearchValueChange = useDebouncedFn((event): void => {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
const value = event?.target?.value || '';
|
||||
|
||||
if (addColumn && addColumn?.onSearch) {
|
||||
|
||||
@@ -50,7 +50,7 @@ function Code({
|
||||
const match = /language-(\w+)/.exec(className || '');
|
||||
return !inline && match ? (
|
||||
<SyntaxHighlighter
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
style={a11yDark}
|
||||
language={match[1]}
|
||||
PreTag="div"
|
||||
@@ -115,7 +115,7 @@ function MarkdownRenderer({
|
||||
className={className}
|
||||
rehypePlugins={[rehypeRaw as any]}
|
||||
components={{
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
a: Link,
|
||||
pre: ({ children }) =>
|
||||
Pre({
|
||||
|
||||
@@ -61,7 +61,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 1. CUSTOM VALUES SUPPORT =====
|
||||
describe('Custom Values Support (CS)', () => {
|
||||
test('CS-01: Custom values persist in selected state', async () => {
|
||||
it('CS-01: Custom values persist in selected state', async () => {
|
||||
const { rerender } = renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -87,7 +87,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(screen.getByText('another-custom')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('CS-02: Partial matches create custom values', async () => {
|
||||
it('CS-02: Partial matches create custom values', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -129,7 +129,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('CS-03: Exact match filtering behavior', async () => {
|
||||
it('CS-03: Exact match filtering behavior', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -176,7 +176,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('CS-04: Search filtering with "end" pattern', async () => {
|
||||
it('CS-04: Search filtering with "end" pattern', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -234,7 +234,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('CS-05: Comma-separated values behavior', async () => {
|
||||
it('CS-05: Comma-separated values behavior', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -281,7 +281,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 2. SEARCH AND FILTERING =====
|
||||
describe('Search and Filtering (SF)', () => {
|
||||
test('SF-01: Selected values pushed to top', async () => {
|
||||
it('SF-01: Selected values pushed to top', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -305,7 +305,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-02: Filtering with search text', async () => {
|
||||
it('SF-02: Filtering with search text', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -350,7 +350,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-03: Highlighting search matches', async () => {
|
||||
it('SF-03: Highlighting search matches', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -381,7 +381,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-04: Search with no results', async () => {
|
||||
it('SF-04: Search with no results', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -424,7 +424,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 3. KEYBOARD NAVIGATION =====
|
||||
describe('Keyboard Navigation (KN)', () => {
|
||||
test('KN-01: Arrow key navigation in dropdown', async () => {
|
||||
it('KN-01: Arrow key navigation in dropdown', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -465,7 +465,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-02: Tab navigation to dropdown', async () => {
|
||||
it('KN-02: Tab navigation to dropdown', async () => {
|
||||
renderWithVirtuoso(
|
||||
<div>
|
||||
<input data-testid="prev-input" />
|
||||
@@ -515,7 +515,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-03: Enter selection in dropdown', async () => {
|
||||
it('KN-03: Enter selection in dropdown', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -540,7 +540,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(mockOnChange).toHaveBeenCalledWith(['frontend'], ['frontend']);
|
||||
});
|
||||
|
||||
test('KN-04: Chip deletion with keyboard', async () => {
|
||||
it('KN-04: Chip deletion with keyboard', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -586,7 +586,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 5. UI/UX BEHAVIORS =====
|
||||
describe('UI/UX Behaviors (UI)', () => {
|
||||
test('UI-01: Loading state does not block interaction', async () => {
|
||||
it('UI-01: Loading state does not block interaction', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -603,7 +603,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-02: Component remains editable in all states', async () => {
|
||||
it('UI-02: Component remains editable in all states', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -634,7 +634,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).not.toBeDisabled();
|
||||
});
|
||||
|
||||
test('UI-03: Toggle/Only labels in dropdown', async () => {
|
||||
it('UI-03: Toggle/Only labels in dropdown', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -656,7 +656,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-04: Should display values with loading info at bottom', async () => {
|
||||
it('UI-04: Should display values with loading info at bottom', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -677,7 +677,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-05: Error state display in footer', async () => {
|
||||
it('UI-05: Error state display in footer', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -696,7 +696,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-06: No data state display', async () => {
|
||||
it('UI-06: No data state display', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={[]}
|
||||
@@ -716,7 +716,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 6. CLEAR ACTIONS =====
|
||||
describe('Clear Actions (CA)', () => {
|
||||
test('CA-01: Ctrl+A selects all chips', async () => {
|
||||
it('CA-01: Ctrl+A selects all chips', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -760,7 +760,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('CA-02: Clear icon removes all selections', async () => {
|
||||
it('CA-02: Clear icon removes all selections', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -777,7 +777,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
}
|
||||
});
|
||||
|
||||
test('CA-03: Individual chip removal', async () => {
|
||||
it('CA-03: Individual chip removal', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -790,7 +790,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
const removeButtons = document.querySelectorAll(
|
||||
'.ant-select-selection-item-remove',
|
||||
);
|
||||
expect(removeButtons.length).toBe(2);
|
||||
expect(removeButtons).toHaveLength(2);
|
||||
|
||||
await user.click(removeButtons[1] as Element);
|
||||
|
||||
@@ -804,7 +804,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 7. SAVE AND SELECTION TRIGGERS =====
|
||||
describe('Save and Selection Triggers (ST)', () => {
|
||||
test('ST-01: ESC triggers save action', async () => {
|
||||
it('ST-01: ESC triggers save action', async () => {
|
||||
const mockDropdownChange = jest.fn();
|
||||
|
||||
renderWithVirtuoso(
|
||||
@@ -837,7 +837,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('ST-02: Mouse selection works', async () => {
|
||||
it('ST-02: Mouse selection works', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -859,7 +859,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('ST-03: ENTER in input field creates custom value', async () => {
|
||||
it('ST-03: ENTER in input field creates custom value', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -892,7 +892,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('ST-04: Search text persistence', async () => {
|
||||
it('ST-04: Search text persistence', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -932,7 +932,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 8. SPECIAL OPTIONS AND STATES =====
|
||||
describe('Special Options and States (SO)', () => {
|
||||
test('SO-01: ALL option appears first and separated', async () => {
|
||||
it('SO-01: ALL option appears first and separated', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -954,7 +954,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SO-02: ALL selection behavior', async () => {
|
||||
it('SO-02: ALL selection behavior', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -981,7 +981,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('SO-03: ALL tag display when all selected', () => {
|
||||
it('SO-03: ALL tag display when all selected', () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -996,7 +996,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(screen.queryByText('frontend')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('SO-04: Footer information display', async () => {
|
||||
it('SO-04: Footer information display', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1017,7 +1017,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== GROUPED OPTIONS SUPPORT =====
|
||||
describe('Grouped Options Support', () => {
|
||||
test('handles grouped options correctly', async () => {
|
||||
it('handles grouped options correctly', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockGroupedOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1041,7 +1041,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== ACCESSIBILITY TESTS =====
|
||||
describe('Accessibility', () => {
|
||||
test('has proper ARIA attributes', async () => {
|
||||
it('has proper ARIA attributes', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1058,7 +1058,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('supports screen reader navigation', async () => {
|
||||
it('supports screen reader navigation', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1079,7 +1079,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 9. ADVANCED KEYBOARD NAVIGATION =====
|
||||
describe('Advanced Keyboard Navigation (AKN)', () => {
|
||||
test('AKN-01: Shift + Arrow + Del chip deletion', async () => {
|
||||
it('AKN-01: Shift + Arrow + Del chip deletion', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -1137,7 +1137,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).toHaveFocus();
|
||||
});
|
||||
|
||||
test('AKN-03: Mouse out closes dropdown', async () => {
|
||||
it('AKN-03: Mouse out closes dropdown', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1164,7 +1164,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 10. ADVANCED FILTERING AND HIGHLIGHTING =====
|
||||
describe('Advanced Filtering and Highlighting (AFH)', () => {
|
||||
test('AFH-01: Highlighted values pushed to top', async () => {
|
||||
it('AFH-01: Highlighted values pushed to top', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1220,7 +1220,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('AFH-02: Distinction between selection Enter and save Enter', async () => {
|
||||
it('AFH-02: Distinction between selection Enter and save Enter', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1267,7 +1267,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 11. ADVANCED CLEAR ACTIONS =====
|
||||
describe('Advanced Clear Actions (ACA)', () => {
|
||||
test('ACA-01: Clear action waiting behavior', async () => {
|
||||
it('ACA-01: Clear action waiting behavior', async () => {
|
||||
const mockOnChangeWithDelay = jest.fn().mockImplementation(
|
||||
() =>
|
||||
new Promise<void>((resolve) => {
|
||||
@@ -1300,7 +1300,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 12. ADVANCED UI STATES =====
|
||||
describe('Advanced UI States (AUS)', () => {
|
||||
test('AUS-01: No data with previous value selected', async () => {
|
||||
it('AUS-01: No data with previous value selected', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={[]}
|
||||
@@ -1322,7 +1322,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(screen.getByText('previous-value')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('AUS-02: Always editable accessibility', async () => {
|
||||
it('AUS-02: Always editable accessibility', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -1338,7 +1338,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).not.toBeDisabled();
|
||||
});
|
||||
|
||||
test('AUS-03: Sufficient space for search value', async () => {
|
||||
it('AUS-03: Sufficient space for search value', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -1372,7 +1372,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 13. REGEX AND CUSTOM VALUES =====
|
||||
describe('Regex and Custom Values (RCV)', () => {
|
||||
test('RCV-01: Regex pattern support', async () => {
|
||||
it('RCV-01: Regex pattern support', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect
|
||||
options={mockOptions}
|
||||
@@ -1418,7 +1418,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('RCV-02: Custom values treated as normal dropdown values', async () => {
|
||||
it('RCV-02: Custom values treated as normal dropdown values', async () => {
|
||||
const customOptions = [
|
||||
...mockOptions,
|
||||
{ label: 'custom-value', value: 'custom-value', type: 'custom' as const },
|
||||
@@ -1456,7 +1456,7 @@ describe('CustomMultiSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 14. DROPDOWN PERSISTENCE =====
|
||||
describe('Dropdown Persistence (DP)', () => {
|
||||
test('DP-01: Dropdown stays open for non-save actions', async () => {
|
||||
it('DP-01: Dropdown stays open for non-save actions', async () => {
|
||||
renderWithVirtuoso(
|
||||
<CustomMultiSelect options={mockOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
|
||||
@@ -50,7 +50,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 1. CUSTOM VALUES SUPPORT =====
|
||||
describe('Custom Values Support (CS)', () => {
|
||||
test('CS-02: Partial matches create custom values', async () => {
|
||||
it('CS-02: Partial matches create custom values', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={mockOptions}
|
||||
@@ -110,7 +110,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('CS-03: Exact match behavior', async () => {
|
||||
it('CS-03: Exact match behavior', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -161,7 +161,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 2. SEARCH AND FILTERING =====
|
||||
describe('Search and Filtering (SF)', () => {
|
||||
test('SF-01: Selected values pushed to top', async () => {
|
||||
it('SF-01: Selected values pushed to top', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={mockOptions}
|
||||
@@ -185,7 +185,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-02: Real-time search filtering', async () => {
|
||||
it('SF-02: Real-time search filtering', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -228,7 +228,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-03: Search highlighting', async () => {
|
||||
it('SF-03: Search highlighting', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -257,7 +257,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('SF-04: Search with partial matches', async () => {
|
||||
it('SF-04: Search with partial matches', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -298,7 +298,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 3. KEYBOARD NAVIGATION =====
|
||||
describe('Keyboard Navigation (KN)', () => {
|
||||
test('KN-01: Arrow key navigation in dropdown', async () => {
|
||||
it('KN-01: Arrow key navigation in dropdown', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -329,7 +329,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-02: Tab navigation to dropdown', async () => {
|
||||
it('KN-02: Tab navigation to dropdown', async () => {
|
||||
render(
|
||||
<div>
|
||||
<input data-testid="prev-input" />
|
||||
@@ -355,7 +355,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-03: Enter selection in dropdown', async () => {
|
||||
it('KN-03: Enter selection in dropdown', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -376,7 +376,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-04: Space key selection', async () => {
|
||||
it('KN-04: Space key selection', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -396,7 +396,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('KN-05: Tab navigation within dropdown', async () => {
|
||||
it('KN-05: Tab navigation within dropdown', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -417,7 +417,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 4. UI/UX BEHAVIORS =====
|
||||
describe('UI/UX Behaviors (UI)', () => {
|
||||
test('UI-01: Loading state does not block interaction', async () => {
|
||||
it('UI-01: Loading state does not block interaction', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -429,7 +429,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).toHaveFocus();
|
||||
});
|
||||
|
||||
test('UI-02: Component remains editable in all states', () => {
|
||||
it('UI-02: Component remains editable in all states', () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={mockOptions}
|
||||
@@ -444,7 +444,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).not.toBeDisabled();
|
||||
});
|
||||
|
||||
test('UI-03: Loading state display in footer', async () => {
|
||||
it('UI-03: Loading state display in footer', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -458,7 +458,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-04: Error state display in footer', async () => {
|
||||
it('UI-04: Error state display in footer', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={mockOptions}
|
||||
@@ -477,7 +477,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('UI-05: No data state display', async () => {
|
||||
it('UI-05: No data state display', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={[]}
|
||||
@@ -497,7 +497,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 6. SAVE AND SELECTION TRIGGERS =====
|
||||
describe('Save and Selection Triggers (ST)', () => {
|
||||
test('ST-01: Mouse selection works', async () => {
|
||||
it('ST-01: Mouse selection works', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -520,7 +520,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 7. GROUPED OPTIONS SUPPORT =====
|
||||
describe('Grouped Options Support', () => {
|
||||
test('handles grouped options correctly', async () => {
|
||||
it('handles grouped options correctly', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockGroupedOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -541,7 +541,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('grouped option selection works', async () => {
|
||||
it('grouped option selection works', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockGroupedOptions} onChange={mockOnChange} />,
|
||||
);
|
||||
@@ -566,7 +566,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 8. ACCESSIBILITY =====
|
||||
describe('Accessibility', () => {
|
||||
test('has proper ARIA attributes', async () => {
|
||||
it('has proper ARIA attributes', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -580,7 +580,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('supports screen reader navigation', async () => {
|
||||
it('supports screen reader navigation', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -596,7 +596,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('has proper focus management', async () => {
|
||||
it('has proper focus management', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -617,7 +617,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 10. EDGE CASES =====
|
||||
describe('Edge Cases', () => {
|
||||
test('handles special characters in options', async () => {
|
||||
it('handles special characters in options', async () => {
|
||||
const specialOptions = [
|
||||
{ label: 'Option with spaces', value: 'option-with-spaces' },
|
||||
{ label: 'Option-with-dashes', value: 'option-with-dashes' },
|
||||
@@ -638,7 +638,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('handles extremely long option labels', async () => {
|
||||
it('handles extremely long option labels', async () => {
|
||||
const longLabelOptions = [
|
||||
{
|
||||
label:
|
||||
@@ -663,7 +663,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 11. ADVANCED KEYBOARD NAVIGATION =====
|
||||
describe('Advanced Keyboard Navigation (AKN)', () => {
|
||||
test('AKN-01: Mouse out closes dropdown', async () => {
|
||||
it('AKN-01: Mouse out closes dropdown', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -684,7 +684,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('AKN-02: TAB navigation from input to dropdown', async () => {
|
||||
it('AKN-02: TAB navigation from input to dropdown', async () => {
|
||||
render(
|
||||
<div>
|
||||
<input data-testid="prev-input" />
|
||||
@@ -722,7 +722,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 12. ADVANCED FILTERING AND HIGHLIGHTING =====
|
||||
describe('Advanced Filtering and Highlighting (AFH)', () => {
|
||||
test('AFH-01: Highlighted values pushed to top', async () => {
|
||||
it('AFH-01: Highlighted values pushed to top', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -776,7 +776,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('AFH-02: Distinction between selection Enter and save Enter', async () => {
|
||||
it('AFH-02: Distinction between selection Enter and save Enter', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -830,7 +830,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 13. ADVANCED CLEAR ACTIONS =====
|
||||
describe('Advanced Clear Actions (ACA)', () => {
|
||||
test('ACA-01: Clear action waiting behavior', async () => {
|
||||
it('ACA-01: Clear action waiting behavior', async () => {
|
||||
const mockOnChangeWithDelay = jest.fn().mockImplementation(
|
||||
() =>
|
||||
new Promise((resolve) => {
|
||||
@@ -860,7 +860,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
expect(mockOnChangeWithDelay).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
test('ACA-02: Single select clear behavior like text input', async () => {
|
||||
it('ACA-02: Single select clear behavior like text input', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={mockOptions}
|
||||
@@ -883,7 +883,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 14. ADVANCED UI STATES =====
|
||||
describe('Advanced UI States (AUS)', () => {
|
||||
test('AUS-01: No data with previous value selected', async () => {
|
||||
it('AUS-01: No data with previous value selected', async () => {
|
||||
render(
|
||||
<CustomSelect
|
||||
options={[]}
|
||||
@@ -905,7 +905,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
expect(screen.getAllByText('previous-value')).toHaveLength(2);
|
||||
});
|
||||
|
||||
test('AUS-02: Always editable accessibility', async () => {
|
||||
it('AUS-02: Always editable accessibility', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -921,7 +921,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
expect(combobox).not.toBeDisabled();
|
||||
});
|
||||
|
||||
test('AUS-03: Sufficient space for search value', async () => {
|
||||
it('AUS-03: Sufficient space for search value', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -950,7 +950,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('AUS-04: No spinners blocking user interaction', async () => {
|
||||
it('AUS-04: No spinners blocking user interaction', async () => {
|
||||
render(
|
||||
<CustomSelect options={mockOptions} onChange={mockOnChange} loading />,
|
||||
);
|
||||
@@ -976,7 +976,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 15. REGEX AND CUSTOM VALUES =====
|
||||
describe('Regex and Custom Values (RCV)', () => {
|
||||
test('RCV-01: Regex pattern support', async () => {
|
||||
it('RCV-01: Regex pattern support', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
@@ -1019,7 +1019,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('RCV-02: Custom values treated as normal dropdown values', async () => {
|
||||
it('RCV-02: Custom values treated as normal dropdown values', async () => {
|
||||
const customOptions = [
|
||||
...mockOptions,
|
||||
{ label: 'custom-value', value: 'custom-value', type: 'custom' as const },
|
||||
@@ -1051,7 +1051,7 @@ describe('CustomSelect - Comprehensive Tests', () => {
|
||||
|
||||
// ===== 16. DROPDOWN PERSISTENCE =====
|
||||
describe('Dropdown Persistence (DP)', () => {
|
||||
test('DP-01: Dropdown closes only on save actions', async () => {
|
||||
it('DP-01: Dropdown closes only on save actions', async () => {
|
||||
render(<CustomSelect options={mockOptions} onChange={mockOnChange} />);
|
||||
|
||||
const combobox = screen.getByRole('combobox');
|
||||
|
||||
@@ -86,7 +86,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 1. INTEGRATION WITH CUSTOMSELECT =====
|
||||
describe('CustomSelect Integration (VI)', () => {
|
||||
test('VI-01: Single select variable integration', async () => {
|
||||
it('VI-01: Single select variable integration', async () => {
|
||||
const variable = createMockVariable({
|
||||
multiSelect: false,
|
||||
type: 'CUSTOM',
|
||||
@@ -130,7 +130,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 2. INTEGRATION WITH CUSTOMMULTISELECT =====
|
||||
describe('CustomMultiSelect Integration (VI)', () => {
|
||||
test('VI-02: Multi select variable integration', async () => {
|
||||
it('VI-02: Multi select variable integration', async () => {
|
||||
const variable = createMockVariable({
|
||||
multiSelect: true,
|
||||
type: 'CUSTOM',
|
||||
@@ -174,7 +174,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 3. TEXTBOX VARIABLE TYPE =====
|
||||
describe('Textbox Variable Integration', () => {
|
||||
test('VI-03: Textbox variable handling', async () => {
|
||||
it('VI-03: Textbox variable handling', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'TEXTBOX',
|
||||
selectedValue: 'initial-value',
|
||||
@@ -219,7 +219,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 4. VALUE PERSISTENCE AND STATE MANAGEMENT =====
|
||||
describe('Value Persistence and State Management', () => {
|
||||
test('VI-04: All selected state handling', () => {
|
||||
it('VI-04: All selected state handling', () => {
|
||||
const variable = createMockVariable({
|
||||
multiSelect: true,
|
||||
type: 'CUSTOM',
|
||||
@@ -243,7 +243,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
expect(screen.getByText('ALL')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('VI-05: Dropdown behavior with temporary selections', async () => {
|
||||
it('VI-05: Dropdown behavior with temporary selections', async () => {
|
||||
const variable = createMockVariable({
|
||||
multiSelect: true,
|
||||
type: 'CUSTOM',
|
||||
@@ -277,7 +277,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 6. ACCESSIBILITY AND USER EXPERIENCE =====
|
||||
describe('Accessibility and User Experience', () => {
|
||||
test('VI-06: Variable description tooltip', async () => {
|
||||
it('VI-06: Variable description tooltip', async () => {
|
||||
const variable = createMockVariable({
|
||||
description: 'This variable controls the service selection',
|
||||
type: 'CUSTOM',
|
||||
@@ -310,7 +310,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('VI-07: Variable name display', () => {
|
||||
it('VI-07: Variable name display', () => {
|
||||
const variable = createMockVariable({
|
||||
name: 'service_name',
|
||||
type: 'CUSTOM',
|
||||
@@ -331,7 +331,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
expect(screen.getByText('$service_name')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('VI-08: Max tag count behavior', async () => {
|
||||
it('VI-08: Max tag count behavior', async () => {
|
||||
const variable = createMockVariable({
|
||||
multiSelect: true,
|
||||
type: 'CUSTOM',
|
||||
@@ -365,7 +365,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 8. SEARCH INTERACTION TESTS =====
|
||||
describe('Search Interaction Tests', () => {
|
||||
test('VI-14: Search persistence across dropdown open/close', async () => {
|
||||
it('VI-14: Search persistence across dropdown open/close', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'CUSTOM',
|
||||
customValue: 'option1,option2,option3',
|
||||
@@ -417,7 +417,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 9. ADVANCED KEYBOARD NAVIGATION =====
|
||||
describe('Advanced Keyboard Navigation (VI)', () => {
|
||||
test('VI-15: Shift + Arrow + Del chip deletion in multiselect', async () => {
|
||||
it('VI-15: Shift + Arrow + Del chip deletion in multiselect', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'CUSTOM',
|
||||
customValue: 'option1,option2,option3',
|
||||
@@ -461,7 +461,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 11. ADVANCED UI STATES =====
|
||||
describe('Advanced UI States (VI)', () => {
|
||||
test('VI-19: No data with previous value selected in variable', async () => {
|
||||
it('VI-19: No data with previous value selected in variable', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'CUSTOM',
|
||||
customValue: '',
|
||||
@@ -499,7 +499,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
expect(combobox).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('VI-20: Always editable accessibility in variable', async () => {
|
||||
it('VI-20: Always editable accessibility in variable', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'CUSTOM',
|
||||
customValue: 'option1,option2',
|
||||
@@ -530,7 +530,7 @@ describe('VariableItem Integration Tests', () => {
|
||||
|
||||
// ===== 13. DROPDOWN PERSISTENCE =====
|
||||
describe('Dropdown Persistence (VI)', () => {
|
||||
test('VI-24: Dropdown stays open for non-save actions in variable', async () => {
|
||||
it('VI-24: Dropdown stays open for non-save actions in variable', async () => {
|
||||
const variable = createMockVariable({
|
||||
type: 'CUSTOM',
|
||||
customValue: 'option1,option2,option3',
|
||||
|
||||
@@ -44,7 +44,7 @@ describe('OverflowInputToolTip', () => {
|
||||
jest.restoreAllMocks();
|
||||
});
|
||||
|
||||
test('shows tooltip when content overflows and input is clamped at maxAutoWidth', async () => {
|
||||
it('shows tooltip when content overflows and input is clamped at maxAutoWidth', async () => {
|
||||
mockOverflow(150, 250); // clientWidth >= maxAutoWidth (150), scrollWidth > clientWidth
|
||||
|
||||
render(<OverflowInputToolTip value="Very long overflowing text" />);
|
||||
@@ -64,7 +64,7 @@ describe('OverflowInputToolTip', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('does NOT show tooltip when content does not overflow', async () => {
|
||||
it('does NOT show tooltip when content does not overflow', async () => {
|
||||
mockOverflow(150, 100); // content fits (scrollWidth <= clientWidth)
|
||||
|
||||
render(<OverflowInputToolTip value="Short text" />);
|
||||
@@ -76,7 +76,7 @@ describe('OverflowInputToolTip', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('does NOT show tooltip when content overflows but input is NOT at maxAutoWidth', async () => {
|
||||
it('does NOT show tooltip when content overflows but input is NOT at maxAutoWidth', async () => {
|
||||
mockOverflow(100, 250); // clientWidth < maxAutoWidth (150), scrollWidth > clientWidth
|
||||
|
||||
render(<OverflowInputToolTip value="Long but input not clamped" />);
|
||||
@@ -88,7 +88,7 @@ describe('OverflowInputToolTip', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('uncontrolled input allows typing', async () => {
|
||||
it('uncontrolled input allows typing', async () => {
|
||||
render(<OverflowInputToolTip defaultValue="Init" />);
|
||||
|
||||
const input = screen.getByRole('textbox') as HTMLInputElement;
|
||||
@@ -97,7 +97,7 @@ describe('OverflowInputToolTip', () => {
|
||||
expect(input).toHaveValue('InitABC');
|
||||
});
|
||||
|
||||
test('disabled input never shows tooltip even if overflowing', async () => {
|
||||
it('disabled input never shows tooltip even if overflowing', async () => {
|
||||
mockOverflow(150, 300);
|
||||
|
||||
render(<OverflowInputToolTip value="Overflowing!" disabled />);
|
||||
@@ -109,7 +109,7 @@ describe('OverflowInputToolTip', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('renders mirror span and input correctly (structural assertions instead of snapshot)', () => {
|
||||
it('renders mirror span and input correctly (structural assertions instead of snapshot)', () => {
|
||||
const { container } = render(<OverflowInputToolTip value="Snapshot" />);
|
||||
const mirror = container.querySelector('.overflow-input-mirror');
|
||||
const input = container.querySelector('input') as HTMLInputElement | null;
|
||||
|
||||
@@ -29,7 +29,7 @@ describe('traceOperatorContextUtils', () => {
|
||||
null,
|
||||
);
|
||||
|
||||
expect(context).toEqual({
|
||||
expect(context).toStrictEqual({
|
||||
tokenType: TraceOperatorGrammarLexer.IDENTIFIER,
|
||||
text: 'test',
|
||||
start: 0,
|
||||
@@ -62,7 +62,7 @@ describe('traceOperatorContextUtils', () => {
|
||||
false,
|
||||
);
|
||||
|
||||
expect(context).toEqual({
|
||||
expect(context).toStrictEqual({
|
||||
tokenType: TraceOperatorGrammarLexer.IDENTIFIER,
|
||||
text: 'test',
|
||||
start: 0,
|
||||
@@ -193,7 +193,7 @@ describe('traceOperatorContextUtils', () => {
|
||||
it('should return default context for empty query', () => {
|
||||
const result = getTraceOperatorContextAtCursor('', 0);
|
||||
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
tokenType: -1,
|
||||
text: '',
|
||||
start: 0,
|
||||
@@ -211,7 +211,7 @@ describe('traceOperatorContextUtils', () => {
|
||||
it('should return default context for null query', () => {
|
||||
const result = getTraceOperatorContextAtCursor(null as any, 0);
|
||||
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
tokenType: -1,
|
||||
text: '',
|
||||
start: 0,
|
||||
@@ -229,7 +229,7 @@ describe('traceOperatorContextUtils', () => {
|
||||
it('should return default context for undefined query', () => {
|
||||
const result = getTraceOperatorContextAtCursor(undefined as any, 0);
|
||||
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
tokenType: -1,
|
||||
text: '',
|
||||
start: 0,
|
||||
|
||||
@@ -8,21 +8,21 @@ const makeTraceOperator = (expression: string): IBuilderTraceOperator =>
|
||||
describe('getInvolvedQueriesInTraceOperator', () => {
|
||||
it('returns empty array for empty input', () => {
|
||||
const result = getInvolvedQueriesInTraceOperator([]);
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('extracts identifiers from expression', () => {
|
||||
const result = getInvolvedQueriesInTraceOperator([
|
||||
makeTraceOperator('A => B'),
|
||||
]);
|
||||
expect(result).toEqual(['A', 'B']);
|
||||
expect(result).toStrictEqual(['A', 'B']);
|
||||
});
|
||||
|
||||
it('extracts identifiers from complex expression', () => {
|
||||
const result = getInvolvedQueriesInTraceOperator([
|
||||
makeTraceOperator('A => (NOT B || C)'),
|
||||
]);
|
||||
expect(result).toEqual(['A', 'B', 'C']);
|
||||
expect(result).toStrictEqual(['A', 'B', 'C']);
|
||||
});
|
||||
|
||||
it('filters out querynames from complex expression', () => {
|
||||
@@ -31,7 +31,7 @@ describe('getInvolvedQueriesInTraceOperator', () => {
|
||||
'(A1 && (NOT B2 || (C3 -> (D4 && E5)))) => ((F6 || G7) && (NOT (H8 -> I9)))',
|
||||
),
|
||||
]);
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
'A1',
|
||||
'B2',
|
||||
'C3',
|
||||
|
||||
@@ -85,7 +85,7 @@ describe('previousQuery.utils', () => {
|
||||
saveAsPreviousQuery(key, sampleQuery);
|
||||
|
||||
const fromStore = getPreviousQueryFromKey(key);
|
||||
expect(fromStore).toEqual(sampleQuery);
|
||||
expect(fromStore).toStrictEqual(sampleQuery);
|
||||
});
|
||||
|
||||
it('saveAsPreviousQuery merges multiple entries and removeKeyFromPreviousQuery deletes one', () => {
|
||||
|
||||
@@ -22,18 +22,20 @@ describe('convertFiltersToExpression', () => {
|
||||
|
||||
it('should handle empty, null, and undefined inputs', () => {
|
||||
// Test null and undefined
|
||||
expect(convertFiltersToExpression(null as any)).toEqual({ expression: '' });
|
||||
expect(convertFiltersToExpression(undefined as any)).toEqual({
|
||||
expect(convertFiltersToExpression(null as any)).toStrictEqual({
|
||||
expression: '',
|
||||
});
|
||||
expect(convertFiltersToExpression(undefined as any)).toStrictEqual({
|
||||
expression: '',
|
||||
});
|
||||
|
||||
// Test empty filters
|
||||
expect(convertFiltersToExpression({ items: [], op: 'AND' })).toEqual({
|
||||
expect(convertFiltersToExpression({ items: [], op: 'AND' })).toStrictEqual({
|
||||
expression: '',
|
||||
});
|
||||
expect(
|
||||
convertFiltersToExpression({ items: undefined, op: 'AND' } as any),
|
||||
).toEqual({ expression: '' });
|
||||
).toStrictEqual({ expression: '' });
|
||||
});
|
||||
|
||||
it('should convert basic comparison operators with proper value formatting', () => {
|
||||
@@ -92,7 +94,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"service = 'api-gateway' AND status != 'error' AND duration > 100 AND count <= 50 AND is_active = true AND enabled = false AND count = 0 AND regex REGEXP '.*'",
|
||||
});
|
||||
@@ -124,7 +126,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"message = 'user\\'s data' AND description = '' AND path = '/api/v1/users'",
|
||||
});
|
||||
@@ -162,7 +164,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"service in ['api-gateway', 'user-service', 'auth-service'] AND status in ['success'] AND tags in [] AND name in ['John\\'s', 'Mary\\'s', 'Bob']",
|
||||
});
|
||||
@@ -224,7 +226,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"service NOT IN ['api-gateway', 'user-service'] AND message NOT LIKE 'error' AND path NOT REGEXP '/api/.*' AND service NOT IN ['api-gateway'] AND user_id NOT EXISTS AND description NOT CONTAINS 'error' AND NOT has(tags, 'production') AND NOT hasAny(labels, ['env:prod', 'service:api'])",
|
||||
});
|
||||
@@ -268,7 +270,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"user_id exists AND user_id exists AND has(tags, 'production') AND hasAny(tags, ['production', 'staging']) AND hasAll(tags, ['production', 'monitoring'])",
|
||||
});
|
||||
@@ -312,7 +314,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"service = 'api-gateway' AND status = 'success' AND service in ['api-gateway']",
|
||||
});
|
||||
@@ -362,7 +364,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"service in ['api-gateway', 'user-service'] AND user_id exists AND has(tags, 'production') AND duration > 100 AND status NOT IN ['error', 'timeout'] AND method = 'POST'",
|
||||
});
|
||||
@@ -412,7 +414,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"count = 0 AND score > 100 AND limit >= 50 AND threshold < 1000 AND max_value <= 999 AND values in ['1', '2', '3', '4', '5']",
|
||||
});
|
||||
@@ -456,7 +458,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"is_active = true AND is_deleted = false AND email = 'user@example.com' AND description = 'Contains \"quotes\" and \\'apostrophes\\'' AND path = '/api/v1/users/123?filter=true'",
|
||||
});
|
||||
@@ -506,7 +508,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"has(tags, 'production') AND hasAny(labels, ['env:prod', 'service:api']) AND hasAll(metadata, ['version:1.0', 'team:backend']) AND services in ['api-gateway', 'user-service', 'auth-service', 'payment-service'] AND excluded_services NOT IN ['legacy-service', 'deprecated-service'] AND status_codes in ['200', '201', '400', '500']",
|
||||
});
|
||||
@@ -544,7 +546,7 @@ describe('convertFiltersToExpression', () => {
|
||||
};
|
||||
|
||||
const result = convertFiltersToExpression(filters);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
expression:
|
||||
"user_id NOT EXISTS AND description NOT CONTAINS 'error' AND NOT has(tags, 'production') AND NOT hasAny(labels, ['env:prod', 'service:api'])",
|
||||
});
|
||||
@@ -568,7 +570,7 @@ describe('convertFiltersToExpression', () => {
|
||||
undefined,
|
||||
);
|
||||
|
||||
expect(result.filters).toEqual(filters);
|
||||
expect(result.filters).toStrictEqual(filters);
|
||||
expect(result.filter.expression).toBe("service.name = 'test-service'");
|
||||
});
|
||||
|
||||
@@ -583,7 +585,7 @@ describe('convertFiltersToExpression', () => {
|
||||
undefined,
|
||||
);
|
||||
|
||||
expect(result.filters).toEqual(filters);
|
||||
expect(result.filters).toStrictEqual(filters);
|
||||
expect(result.filter.expression).toBe('');
|
||||
});
|
||||
|
||||
@@ -611,7 +613,7 @@ describe('convertFiltersToExpression', () => {
|
||||
expect(result.filter).toBeDefined();
|
||||
expect(result.filter.expression).toBe("service.name = 'updated-service'");
|
||||
// Ensure parser can parse the existing query
|
||||
expect(extractQueryPairs(existingQuery)).toEqual(
|
||||
expect(extractQueryPairs(existingQuery)).toStrictEqual(
|
||||
expect.arrayContaining([
|
||||
expect.objectContaining({
|
||||
key: 'service.name',
|
||||
@@ -805,7 +807,7 @@ describe('convertAggregationToExpression', () => {
|
||||
temporality: 'delta',
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
metricName: 'test_metric',
|
||||
timeAggregation: 'avg',
|
||||
@@ -825,9 +827,11 @@ describe('convertAggregationToExpression', () => {
|
||||
spaceAggregation: 'noop',
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
metricName: 'test_metric',
|
||||
reduceTo: undefined,
|
||||
temporality: undefined,
|
||||
timeAggregation: 'count',
|
||||
spaceAggregation: 'count',
|
||||
},
|
||||
@@ -841,9 +845,11 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.METRICS,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
metricName: '',
|
||||
reduceTo: undefined,
|
||||
temporality: undefined,
|
||||
timeAggregation: 'sum',
|
||||
spaceAggregation: 'sum',
|
||||
},
|
||||
@@ -858,7 +864,7 @@ describe('convertAggregationToExpression', () => {
|
||||
alias: 'trace_alias',
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'count(test_metric)',
|
||||
alias: 'trace_alias',
|
||||
@@ -874,7 +880,7 @@ describe('convertAggregationToExpression', () => {
|
||||
alias: 'log_alias',
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'avg(test_metric)',
|
||||
alias: 'log_alias',
|
||||
@@ -889,7 +895,7 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.TRACES,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'count()',
|
||||
},
|
||||
@@ -903,7 +909,7 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.LOGS,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'sum(test_metric)',
|
||||
},
|
||||
@@ -917,9 +923,11 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.METRICS,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
metricName: 'test_metric',
|
||||
reduceTo: undefined,
|
||||
temporality: undefined,
|
||||
timeAggregation: 'max',
|
||||
spaceAggregation: 'max',
|
||||
},
|
||||
@@ -933,7 +941,7 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.METRICS,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
metricName: 'test_metric',
|
||||
timeAggregation: 'sum',
|
||||
@@ -951,7 +959,7 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.TRACES,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'count()',
|
||||
},
|
||||
@@ -965,7 +973,7 @@ describe('convertAggregationToExpression', () => {
|
||||
dataSource: DataSource.LOGS,
|
||||
});
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
expression: 'count()',
|
||||
},
|
||||
|
||||
@@ -471,6 +471,6 @@ describe('CheckboxFilter - User Flows', () => {
|
||||
|
||||
expect(filterForServiceName.key.key).toBe(SERVICE_NAME_KEY);
|
||||
expect(filterForServiceName.op).toBe('in');
|
||||
expect(filterForServiceName.value).toEqual(['mq-kafka', 'otel-demo']);
|
||||
expect(filterForServiceName.value).toStrictEqual(['mq-kafka', 'otel-demo']);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -323,7 +323,9 @@ describe('Quick Filters with custom filters', () => {
|
||||
const settingsButton = icon.closest('button') ?? icon;
|
||||
await user.click(settingsButton);
|
||||
|
||||
expect(await screen.findByText('Edit quick filters')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('Edit quick filters'),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const addedSection = screen.getByText(ADDED_FILTERS_LABEL).parentElement!;
|
||||
expect(addedSection).toContainElement(
|
||||
@@ -454,7 +456,7 @@ describe('Quick Filters with custom filters', () => {
|
||||
});
|
||||
|
||||
const requestBody = putHandler.mock.calls[0][0];
|
||||
expect(requestBody.filters).toEqual(
|
||||
expect(requestBody.filters).toStrictEqual(
|
||||
expect.arrayContaining([
|
||||
expect.not.objectContaining({ key: FILTER_OS_DESCRIPTION }),
|
||||
]),
|
||||
@@ -535,12 +537,16 @@ describe('Quick Filters refetch behavior', () => {
|
||||
);
|
||||
|
||||
const { unmount } = render(<TestQuickFilters signal={SIGNAL} />);
|
||||
expect(await screen.findByText(FILTER_SERVICE_NAME)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(FILTER_SERVICE_NAME),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
unmount();
|
||||
|
||||
render(<TestQuickFilters signal={SIGNAL} />);
|
||||
expect(await screen.findByText(FILTER_SERVICE_NAME)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(FILTER_SERVICE_NAME),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
expect(getCalls).toBe(2);
|
||||
});
|
||||
@@ -578,7 +584,9 @@ describe('Quick Filters refetch behavior', () => {
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<TestQuickFilters signal={SIGNAL} />);
|
||||
|
||||
expect(await screen.findByText(FILTER_SERVICE_NAME)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(FILTER_SERVICE_NAME),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const icon = await screen.findByTestId(SETTINGS_ICON_TEST_ID);
|
||||
const settingsButton = icon.closest('button') ?? icon;
|
||||
@@ -628,7 +636,9 @@ describe('Quick Filters refetch behavior', () => {
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<TestQuickFilters signal={SIGNAL} />);
|
||||
|
||||
expect(await screen.findByText(FILTER_SERVICE_NAME)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(FILTER_SERVICE_NAME),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const icon = await screen.findByTestId(SETTINGS_ICON_TEST_ID);
|
||||
const settingsButton = icon.closest('button') ?? icon;
|
||||
@@ -657,6 +667,8 @@ describe('Quick Filters refetch behavior', () => {
|
||||
|
||||
render(<TestQuickFilters signal={SIGNAL} config={[]} />);
|
||||
|
||||
expect(await screen.findByText('No filters found')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('No filters found'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -28,7 +28,7 @@ const testRoutes: RouteTabProps['routes'] = [
|
||||
];
|
||||
|
||||
describe('RouteTab component', () => {
|
||||
test('renders correctly', () => {
|
||||
it('renders correctly', () => {
|
||||
const history = createMemoryHistory();
|
||||
render(
|
||||
<Router history={history}>
|
||||
@@ -39,7 +39,7 @@ describe('RouteTab component', () => {
|
||||
expect(screen.getByRole('tab', { name: 'Tab2' })).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('renders correct number of tabs', () => {
|
||||
it('renders correct number of tabs', () => {
|
||||
const history = createMemoryHistory();
|
||||
render(
|
||||
<Router history={history}>
|
||||
@@ -47,10 +47,10 @@ describe('RouteTab component', () => {
|
||||
</Router>,
|
||||
);
|
||||
const tabs = screen.getAllByRole('tab');
|
||||
expect(tabs.length).toBe(testRoutes.length);
|
||||
expect(tabs).toHaveLength(testRoutes.length);
|
||||
});
|
||||
|
||||
test('sets provided activeKey as active tab', () => {
|
||||
it('sets provided activeKey as active tab', () => {
|
||||
const history = createMemoryHistory();
|
||||
render(
|
||||
<Router history={history}>
|
||||
@@ -62,7 +62,7 @@ describe('RouteTab component', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('navigates to correct route on tab click', () => {
|
||||
it('navigates to correct route on tab click', () => {
|
||||
const history = createMemoryHistory();
|
||||
render(
|
||||
<Router history={history}>
|
||||
@@ -74,7 +74,7 @@ describe('RouteTab component', () => {
|
||||
expect(history.location.pathname).toBe('/tab2');
|
||||
});
|
||||
|
||||
test('calls onChangeHandler on tab change', () => {
|
||||
it('calls onChangeHandler on tab change', () => {
|
||||
const onChangeHandler = jest.fn();
|
||||
const history = createMemoryHistory();
|
||||
render(
|
||||
|
||||
@@ -70,9 +70,9 @@ describe('EditKeyModal (URL-controlled)', () => {
|
||||
it('renders key data from prop when edit-key param is set', async () => {
|
||||
renderModal();
|
||||
|
||||
expect(
|
||||
await screen.findByDisplayValue('Original Key Name'),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByDisplayValue('Original Key Name'),
|
||||
).resolves.toBeInTheDocument();
|
||||
expect(screen.getByRole('button', { name: /Save Changes/i })).toBeDisabled();
|
||||
});
|
||||
|
||||
@@ -111,7 +111,7 @@ describe('EditKeyModal (URL-controlled)', () => {
|
||||
|
||||
const latestUrlUpdate =
|
||||
onUrlUpdate.mock.calls[onUrlUpdate.mock.calls.length - 1]?.[0];
|
||||
expect(latestUrlUpdate).toEqual(
|
||||
expect(latestUrlUpdate).toStrictEqual(
|
||||
expect.objectContaining({
|
||||
queryString: expect.any(String),
|
||||
}),
|
||||
@@ -134,9 +134,9 @@ describe('EditKeyModal (URL-controlled)', () => {
|
||||
await user.click(screen.getByRole('button', { name: /Revoke Key/i }));
|
||||
|
||||
// Same dialog, now showing revoke confirmation
|
||||
expect(
|
||||
await screen.findByRole('dialog', { name: /Revoke Original Key Name/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('dialog', { name: /Revoke Original Key Name/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByText(/Revoking this key will permanently invalidate it/i),
|
||||
).toBeInTheDocument();
|
||||
|
||||
@@ -104,7 +104,9 @@ describe('ServiceAccountDrawer', () => {
|
||||
it('renders Overview tab by default: editable name input, locked email, Save disabled when not dirty', async () => {
|
||||
renderDrawer();
|
||||
|
||||
expect(await screen.findByDisplayValue('CI Bot')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByDisplayValue('CI Bot'),
|
||||
).resolves.toBeInTheDocument();
|
||||
expect(screen.getByText('ci-bot@signoz.io')).toBeInTheDocument();
|
||||
expect(screen.getByRole('button', { name: /Save Changes/i })).toBeDisabled();
|
||||
});
|
||||
@@ -272,11 +274,11 @@ describe('ServiceAccountDrawer', () => {
|
||||
|
||||
renderDrawer();
|
||||
|
||||
expect(
|
||||
await screen.findByText(
|
||||
await expect(
|
||||
screen.findByText(
|
||||
/An unexpected error occurred while fetching service account details/i,
|
||||
),
|
||||
).toBeInTheDocument();
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -349,11 +351,11 @@ describe('ServiceAccountDrawer – save-error UX', () => {
|
||||
await waitFor(() => expect(saveBtn).not.toBeDisabled());
|
||||
await user.click(saveBtn);
|
||||
|
||||
expect(
|
||||
await screen.findByText(/Name update.*name update failed/i, undefined, {
|
||||
await expect(
|
||||
screen.findByText(/Name update.*name update failed/i, undefined, {
|
||||
timeout: 5000,
|
||||
}),
|
||||
).toBeInTheDocument();
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('role add failure shows SaveErrorItem with the role name context', async () => {
|
||||
@@ -385,15 +387,11 @@ describe('ServiceAccountDrawer – save-error UX', () => {
|
||||
await waitFor(() => expect(saveBtn).not.toBeDisabled());
|
||||
await user.click(saveBtn);
|
||||
|
||||
expect(
|
||||
await screen.findByText(
|
||||
/Role 'signoz-viewer'.*role assign failed/i,
|
||||
undefined,
|
||||
{
|
||||
timeout: 5000,
|
||||
},
|
||||
),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/Role 'signoz-viewer'.*role assign failed/i, undefined, {
|
||||
timeout: 5000,
|
||||
}),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('role add retries on 429 then succeeds without showing an error', async () => {
|
||||
|
||||
@@ -63,7 +63,9 @@ describe('TanStackCustomTableRow', () => {
|
||||
</tbody>
|
||||
</table>,
|
||||
);
|
||||
expect(await screen.findByTestId('mocked-row-cells')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByTestId('mocked-row-cells'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('applies active class when isRowActive returns true', () => {
|
||||
|
||||
@@ -183,7 +183,7 @@ describe('TanStackRowCells', () => {
|
||||
</tbody>
|
||||
</table>,
|
||||
);
|
||||
expect(await screen.findByText('expanded-r1')).toBeInTheDocument();
|
||||
await expect(screen.findByText('expanded-r1')).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
describe('new tab click', () => {
|
||||
|
||||
@@ -36,7 +36,7 @@ describe('useColumnState', () => {
|
||||
renderHook(() => useColumnState({ storageKey: TEST_KEY, columns }));
|
||||
|
||||
const state = useColumnStore.getState().tables[TEST_KEY];
|
||||
expect(state.hiddenColumnIds).toEqual(['b']);
|
||||
expect(state.hiddenColumnIds).toStrictEqual(['b']);
|
||||
});
|
||||
|
||||
it('does not initialize without storageKey', () => {
|
||||
@@ -61,7 +61,7 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns }),
|
||||
);
|
||||
|
||||
expect(result.current.columnVisibility).toEqual({ b: false });
|
||||
expect(result.current.columnVisibility).toStrictEqual({ b: false });
|
||||
});
|
||||
|
||||
it('applies visibilityBehavior for grouped state', () => {
|
||||
@@ -79,13 +79,15 @@ describe('useColumnState', () => {
|
||||
const { result: notGrouped } = renderHook(() =>
|
||||
useColumnState({ storageKey: TEST_KEY, columns, isGrouped: false }),
|
||||
);
|
||||
expect(notGrouped.current.columnVisibility).toEqual({ grouped: false });
|
||||
expect(notGrouped.current.columnVisibility).toStrictEqual({
|
||||
grouped: false,
|
||||
});
|
||||
|
||||
// Grouped
|
||||
const { result: grouped } = renderHook(() =>
|
||||
useColumnState({ storageKey: TEST_KEY, columns, isGrouped: true }),
|
||||
);
|
||||
expect(grouped.current.columnVisibility).toEqual({ ungrouped: false });
|
||||
expect(grouped.current.columnVisibility).toStrictEqual({ ungrouped: false });
|
||||
});
|
||||
|
||||
it('combines store hidden + visibilityBehavior', () => {
|
||||
@@ -103,7 +105,10 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns, isGrouped: true }),
|
||||
);
|
||||
|
||||
expect(result.current.columnVisibility).toEqual({ a: false, b: false });
|
||||
expect(result.current.columnVisibility).toStrictEqual({
|
||||
a: false,
|
||||
b: false,
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -119,7 +124,7 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns }),
|
||||
);
|
||||
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toEqual([
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toStrictEqual([
|
||||
'a',
|
||||
'b',
|
||||
'c',
|
||||
@@ -138,7 +143,7 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns }),
|
||||
);
|
||||
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toEqual([
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toStrictEqual([
|
||||
'c',
|
||||
'a',
|
||||
'b',
|
||||
@@ -157,7 +162,7 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns }),
|
||||
);
|
||||
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toEqual([
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toStrictEqual([
|
||||
'pinned',
|
||||
'b',
|
||||
'a',
|
||||
@@ -181,7 +186,7 @@ describe('useColumnState', () => {
|
||||
result.current.hideColumn('a');
|
||||
});
|
||||
|
||||
expect(result.current.columnVisibility).toEqual({ a: false });
|
||||
expect(result.current.columnVisibility).toStrictEqual({ a: false });
|
||||
});
|
||||
|
||||
it('showColumn shows a column', () => {
|
||||
@@ -195,13 +200,13 @@ describe('useColumnState', () => {
|
||||
useColumnState({ storageKey: TEST_KEY, columns }),
|
||||
);
|
||||
|
||||
expect(result.current.columnVisibility).toEqual({ a: false });
|
||||
expect(result.current.columnVisibility).toStrictEqual({ a: false });
|
||||
|
||||
act(() => {
|
||||
result.current.showColumn('a');
|
||||
});
|
||||
|
||||
expect(result.current.columnVisibility).toEqual({});
|
||||
expect(result.current.columnVisibility).toStrictEqual({});
|
||||
});
|
||||
|
||||
it('setColumnSizing updates sizing', () => {
|
||||
@@ -219,7 +224,7 @@ describe('useColumnState', () => {
|
||||
result.current.setColumnSizing({ a: 200 });
|
||||
});
|
||||
|
||||
expect(result.current.columnSizing).toEqual({ a: 200 });
|
||||
expect(result.current.columnSizing).toStrictEqual({ a: 200 });
|
||||
});
|
||||
|
||||
it('setColumnOrder updates order from column array', () => {
|
||||
@@ -237,7 +242,7 @@ describe('useColumnState', () => {
|
||||
result.current.setColumnOrder([col('c'), col('a'), col('b')]);
|
||||
});
|
||||
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toEqual([
|
||||
expect(result.current.sortedColumns.map((c) => c.id)).toStrictEqual([
|
||||
'c',
|
||||
'a',
|
||||
'b',
|
||||
|
||||
@@ -29,9 +29,9 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const state = useColumnStore.getState().tables[TEST_KEY];
|
||||
expect(state.hiddenColumnIds).toEqual(['b']);
|
||||
expect(state.columnOrder).toEqual([]);
|
||||
expect(state.columnSizing).toEqual({});
|
||||
expect(state.hiddenColumnIds).toStrictEqual(['b']);
|
||||
expect(state.columnOrder).toStrictEqual([]);
|
||||
expect(state.columnSizing).toStrictEqual({});
|
||||
});
|
||||
|
||||
it('does not reinitialize if already exists', () => {
|
||||
@@ -124,7 +124,9 @@ describe('useColumnStore', () => {
|
||||
.getState()
|
||||
.setColumnSizing(TEST_KEY, { col1: 200, col2: 300 });
|
||||
});
|
||||
expect(useColumnStore.getState().tables[TEST_KEY].columnSizing).toEqual({
|
||||
expect(
|
||||
useColumnStore.getState().tables[TEST_KEY].columnSizing,
|
||||
).toStrictEqual({
|
||||
col1: 200,
|
||||
col2: 300,
|
||||
});
|
||||
@@ -144,11 +146,9 @@ describe('useColumnStore', () => {
|
||||
.getState()
|
||||
.setColumnOrder(TEST_KEY, ['col2', 'col1', 'col3']);
|
||||
});
|
||||
expect(useColumnStore.getState().tables[TEST_KEY].columnOrder).toEqual([
|
||||
'col2',
|
||||
'col1',
|
||||
'col3',
|
||||
]);
|
||||
expect(useColumnStore.getState().tables[TEST_KEY].columnOrder).toStrictEqual(
|
||||
['col2', 'col1', 'col3'],
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -172,9 +172,9 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const state = useColumnStore.getState().tables[TEST_KEY];
|
||||
expect(state.hiddenColumnIds).toEqual(['a']);
|
||||
expect(state.columnOrder).toEqual([]);
|
||||
expect(state.columnSizing).toEqual({});
|
||||
expect(state.hiddenColumnIds).toStrictEqual(['a']);
|
||||
expect(state.columnOrder).toStrictEqual([]);
|
||||
expect(state.columnSizing).toStrictEqual({});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -195,7 +195,7 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const state = useColumnStore.getState().tables[TEST_KEY];
|
||||
expect(state.hiddenColumnIds).toEqual(['col1', 'col3']);
|
||||
expect(state.hiddenColumnIds).toStrictEqual(['col1', 'col3']);
|
||||
expect(state.hiddenColumnIds).not.toContain('col2');
|
||||
});
|
||||
|
||||
@@ -216,7 +216,7 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const stateAfter = useColumnStore.getState().tables[TEST_KEY];
|
||||
expect(stateAfter.hiddenColumnIds).toEqual(hiddenBefore);
|
||||
expect(stateAfter.hiddenColumnIds).toStrictEqual(hiddenBefore);
|
||||
});
|
||||
|
||||
it('does nothing for unknown storage key', () => {
|
||||
@@ -242,7 +242,7 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const { result } = renderHook(() => useHiddenColumnIds(TEST_KEY));
|
||||
expect(result.current).toEqual(['a']);
|
||||
expect(result.current).toStrictEqual(['a']);
|
||||
});
|
||||
|
||||
it('useHiddenColumnIds returns a stable snapshot for persisted state', () => {
|
||||
@@ -270,7 +270,7 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const { result } = renderHook(() => useColumnSizing(TEST_KEY));
|
||||
expect(result.current).toEqual({ col1: 150 });
|
||||
expect(result.current).toStrictEqual({ col1: 150 });
|
||||
});
|
||||
|
||||
it('useColumnOrder returns order', () => {
|
||||
@@ -280,7 +280,7 @@ describe('useColumnStore', () => {
|
||||
});
|
||||
|
||||
const { result } = renderHook(() => useColumnOrder(TEST_KEY));
|
||||
expect(result.current).toEqual(['c', 'b', 'a']);
|
||||
expect(result.current).toStrictEqual(['c', 'b', 'a']);
|
||||
});
|
||||
|
||||
it('returns empty defaults for unknown storageKey', () => {
|
||||
@@ -288,9 +288,9 @@ describe('useColumnStore', () => {
|
||||
const { result: sizing } = renderHook(() => useColumnSizing('unknown'));
|
||||
const { result: order } = renderHook(() => useColumnOrder('unknown'));
|
||||
|
||||
expect(hidden.current).toEqual([]);
|
||||
expect(sizing.current).toEqual({});
|
||||
expect(order.current).toEqual([]);
|
||||
expect(hidden.current).toStrictEqual([]);
|
||||
expect(sizing.current).toStrictEqual({});
|
||||
expect(order.current).toStrictEqual([]);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -80,7 +80,10 @@ describe('useTableParams (local mode — enableQueryParams not set)', () => {
|
||||
act(() => {
|
||||
result.current.setOrderBy({ columnName: 'cpu', order: 'desc' });
|
||||
});
|
||||
expect(result.current.orderBy).toEqual({ columnName: 'cpu', order: 'desc' });
|
||||
expect(result.current.orderBy).toStrictEqual({
|
||||
columnName: 'cpu',
|
||||
order: 'desc',
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -143,7 +146,10 @@ describe('useTableParams (URL mode — enableQueryParams set)', () => {
|
||||
const orderBy = JSON.stringify({ columnName: 'name', order: 'desc' });
|
||||
const wrapper = createNuqsWrapper({ order_by: orderBy });
|
||||
const { result } = renderHook(() => useTableParams(true), { wrapper });
|
||||
expect(result.current.orderBy).toEqual({ columnName: 'name', order: 'desc' });
|
||||
expect(result.current.orderBy).toStrictEqual({
|
||||
columnName: 'name',
|
||||
order: 'desc',
|
||||
});
|
||||
});
|
||||
|
||||
it('updates URL when setPage is called', () => {
|
||||
@@ -178,7 +184,7 @@ describe('useTableParams (URL mode — enableQueryParams set)', () => {
|
||||
.filter(Boolean)
|
||||
.pop();
|
||||
expect(lastOrderBy).toBeDefined();
|
||||
expect(JSON.parse(lastOrderBy!)).toEqual({
|
||||
expect(JSON.parse(lastOrderBy!)).toStrictEqual({
|
||||
columnName: 'value',
|
||||
order: 'asc',
|
||||
});
|
||||
@@ -207,7 +213,7 @@ describe('useTableParams (URL mode — enableQueryParams set)', () => {
|
||||
result.current.setExpanded({ 'row-1': true });
|
||||
});
|
||||
|
||||
expect(result.current.expanded).toEqual({ 'row-1': true });
|
||||
expect(result.current.expanded).toStrictEqual({ 'row-1': true });
|
||||
});
|
||||
|
||||
it('toggles sort order correctly: null → asc → desc → null', () => {
|
||||
@@ -222,13 +228,19 @@ describe('useTableParams (URL mode — enableQueryParams set)', () => {
|
||||
act(() => {
|
||||
result.current.setOrderBy({ columnName: 'id', order: 'asc' });
|
||||
});
|
||||
expect(result.current.orderBy).toEqual({ columnName: 'id', order: 'asc' });
|
||||
expect(result.current.orderBy).toStrictEqual({
|
||||
columnName: 'id',
|
||||
order: 'asc',
|
||||
});
|
||||
|
||||
// Second click: asc → desc
|
||||
act(() => {
|
||||
result.current.setOrderBy({ columnName: 'id', order: 'desc' });
|
||||
});
|
||||
expect(result.current.orderBy).toEqual({ columnName: 'id', order: 'desc' });
|
||||
expect(result.current.orderBy).toStrictEqual({
|
||||
columnName: 'id',
|
||||
order: 'desc',
|
||||
});
|
||||
|
||||
// Third click: desc → null
|
||||
act(() => {
|
||||
|
||||
@@ -8,7 +8,7 @@ import { formatUniversalUnit } from '../formatter';
|
||||
|
||||
describe('formatUniversalUnit', () => {
|
||||
describe('Time', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Days
|
||||
[31, UniversalYAxisUnit.DAYS, '4.43 weeks'],
|
||||
[7, UniversalYAxisUnit.DAYS, '1 week'],
|
||||
@@ -48,7 +48,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Data', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Bytes
|
||||
[864, UniversalYAxisUnit.BYTES, '864 B'],
|
||||
[1000, UniversalYAxisUnit.BYTES, '1 kB'],
|
||||
@@ -91,7 +91,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Data rate', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Bytes/second
|
||||
[864, UniversalYAxisUnit.BYTES_SECOND, '864 B/s'],
|
||||
[1000, UniversalYAxisUnit.BYTES_SECOND, '1 kB/s'],
|
||||
@@ -134,7 +134,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Bit', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Bits
|
||||
[1, UniversalYAxisUnit.BITS, '1 b'],
|
||||
[250, UniversalYAxisUnit.BITS, '250 b'],
|
||||
@@ -186,7 +186,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Bit rate', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Bits/second
|
||||
[512, UniversalYAxisUnit.BITS_SECOND, '512 b/s'],
|
||||
[1000, UniversalYAxisUnit.BITS_SECOND, '1 kb/s'],
|
||||
@@ -236,7 +236,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Count', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[100, UniversalYAxisUnit.COUNT, '100'],
|
||||
[875, UniversalYAxisUnit.COUNT, '875'],
|
||||
[1000, UniversalYAxisUnit.COUNT, '1 K'],
|
||||
@@ -256,7 +256,7 @@ describe('formatUniversalUnit', () => {
|
||||
expect(formatUniversalUnit(value, unit)).toBe(expected);
|
||||
});
|
||||
|
||||
test.each([
|
||||
it.each([
|
||||
[100, UniversalYAxisUnit.COUNT_SECOND, '100 c/s'],
|
||||
[875, UniversalYAxisUnit.COUNT_SECOND, '875 c/s'],
|
||||
[1000, UniversalYAxisUnit.COUNT_SECOND, '1K c/s'],
|
||||
@@ -267,7 +267,7 @@ describe('formatUniversalUnit', () => {
|
||||
expect(formatUniversalUnit(value, unit)).toBe(expected);
|
||||
});
|
||||
|
||||
test.each([
|
||||
it.each([
|
||||
[100, UniversalYAxisUnit.COUNT_MINUTE, '100 c/m'],
|
||||
[875, UniversalYAxisUnit.COUNT_MINUTE, '875 c/m'],
|
||||
[1000, UniversalYAxisUnit.COUNT_MINUTE, '1K c/m'],
|
||||
@@ -280,7 +280,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Operations units', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[780, UniversalYAxisUnit.OPS_SECOND, '780 ops/s'],
|
||||
[1000, UniversalYAxisUnit.OPS_SECOND, '1K ops/s'],
|
||||
[520, UniversalYAxisUnit.OPS_MINUTE, '520 ops/m'],
|
||||
@@ -297,7 +297,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Request units', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[615, UniversalYAxisUnit.REQUESTS_SECOND, '615 req/s'],
|
||||
[1000, UniversalYAxisUnit.REQUESTS_SECOND, '1K req/s'],
|
||||
[480, UniversalYAxisUnit.REQUESTS_MINUTE, '480 req/m'],
|
||||
@@ -311,7 +311,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Read/Write units', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[505, UniversalYAxisUnit.READS_SECOND, '505 rd/s'],
|
||||
[1000, UniversalYAxisUnit.READS_SECOND, '1K rd/s'],
|
||||
[610, UniversalYAxisUnit.WRITES_SECOND, '610 wr/s'],
|
||||
@@ -335,7 +335,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('IO Operations units', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[777, UniversalYAxisUnit.IOOPS_SECOND, '777 io/s'],
|
||||
[1000, UniversalYAxisUnit.IOOPS_SECOND, '1K io/s'],
|
||||
[2500, UniversalYAxisUnit.IOOPS_SECOND, '2.5K io/s'],
|
||||
@@ -363,7 +363,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Time (additional)', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[900, UniversalYAxisUnit.DURATION_MS, '900 milliseconds'],
|
||||
[1000, UniversalYAxisUnit.DURATION_MS, '1 second'],
|
||||
[1, UniversalYAxisUnit.DURATION_MS, '1 millisecond'],
|
||||
@@ -388,7 +388,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Data (IEC/Binary)', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Bytes
|
||||
[900, UniversalYAxisUnit.BYTES_IEC, '900 B'],
|
||||
[1024, UniversalYAxisUnit.BYTES_IEC, '1 KiB'],
|
||||
@@ -430,7 +430,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Data Rate (IEC/Binary)', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Kibibytes/second
|
||||
[900, UniversalYAxisUnit.KIBIBYTES_SECOND, '900 KiB/s'],
|
||||
[1024, UniversalYAxisUnit.KIBIBYTES_SECOND, '1 MiB/s'],
|
||||
@@ -473,7 +473,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Bits (IEC)', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[900, UniversalYAxisUnit.BITS_IEC, '900 b'],
|
||||
[1024, UniversalYAxisUnit.BITS_IEC, '1 Kib'],
|
||||
[1080, UniversalYAxisUnit.BITS_IEC, '1.05 Kib'],
|
||||
@@ -483,7 +483,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Hash Rate', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// Hashes/second
|
||||
[412, UniversalYAxisUnit.HASH_RATE_HASHES_PER_SECOND, '412 H/s'],
|
||||
[1000, UniversalYAxisUnit.HASH_RATE_HASHES_PER_SECOND, '1 kH/s'],
|
||||
@@ -518,7 +518,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Miscellaneous', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[742, UniversalYAxisUnit.MISC_STRING, '742'],
|
||||
[688, UniversalYAxisUnit.MISC_SHORT, '688'],
|
||||
[555, UniversalYAxisUnit.MISC_HUMIDITY, '555 %H'],
|
||||
@@ -534,7 +534,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Acceleration', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[
|
||||
875,
|
||||
UniversalYAxisUnit.ACCELERATION_METERS_PER_SECOND_SQUARED,
|
||||
@@ -553,7 +553,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Angular', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[415, UniversalYAxisUnit.ANGULAR_DEGREE, '415 °'],
|
||||
[732, UniversalYAxisUnit.ANGULAR_RADIAN, '732 rad'],
|
||||
[128, UniversalYAxisUnit.ANGULAR_GRADIAN, '128 grad'],
|
||||
@@ -565,7 +565,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Area', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[210, UniversalYAxisUnit.AREA_SQUARE_METERS, '210 m²'],
|
||||
[152, UniversalYAxisUnit.AREA_SQUARE_FEET, '152 ft²'],
|
||||
[64, UniversalYAxisUnit.AREA_SQUARE_MILES, '64 mi²'],
|
||||
@@ -575,7 +575,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('FLOPs', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
// FLOPS
|
||||
[150, UniversalYAxisUnit.FLOPS_FLOPS, '150 FLOPS'],
|
||||
[1000, UniversalYAxisUnit.FLOPS_FLOPS, '1 kFLOPS'],
|
||||
@@ -613,7 +613,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Concentration', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[415, UniversalYAxisUnit.CONCENTRATION_PPM, '415 ppm'],
|
||||
[1000, UniversalYAxisUnit.CONCENTRATION_PPM, '1000 ppm'],
|
||||
[732, UniversalYAxisUnit.CONCENTRATION_PPB, '732 ppb'],
|
||||
@@ -650,7 +650,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Currency', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[812, UniversalYAxisUnit.CURRENCY_USD, '$812'],
|
||||
[645, UniversalYAxisUnit.CURRENCY_GBP, '£645'],
|
||||
[731, UniversalYAxisUnit.CURRENCY_EUR, '€731'],
|
||||
@@ -688,7 +688,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Power/Electrical', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[715, UniversalYAxisUnit.POWER_WATT, '715 W'],
|
||||
[1000, UniversalYAxisUnit.POWER_WATT, '1 kW'],
|
||||
[1080, UniversalYAxisUnit.POWER_WATT, '1.08 kW'],
|
||||
@@ -744,7 +744,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Flow', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[512, UniversalYAxisUnit.FLOW_GALLONS_PER_MINUTE, '512 gpm'],
|
||||
[1000, UniversalYAxisUnit.FLOW_GALLONS_PER_MINUTE, '1000 gpm'],
|
||||
[678, UniversalYAxisUnit.FLOW_CUBIC_METERS_PER_SECOND, '678 cms'],
|
||||
@@ -766,7 +766,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Force', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[845, UniversalYAxisUnit.FORCE_NEWTON_METERS, '845 Nm'],
|
||||
[1000, UniversalYAxisUnit.FORCE_NEWTON_METERS, '1 kNm'],
|
||||
[1080, UniversalYAxisUnit.FORCE_NEWTON_METERS, '1.08 kNm'],
|
||||
@@ -782,7 +782,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Mass', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[120, UniversalYAxisUnit.MASS_MILLIGRAM, '120 mg'],
|
||||
[120000, UniversalYAxisUnit.MASS_MILLIGRAM, '120 g'],
|
||||
[987, UniversalYAxisUnit.MASS_GRAM, '987 g'],
|
||||
@@ -796,7 +796,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Length', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[88, UniversalYAxisUnit.LENGTH_MILLIMETER, '88 mm'],
|
||||
[100, UniversalYAxisUnit.LENGTH_MILLIMETER, '100 mm'],
|
||||
[1000, UniversalYAxisUnit.LENGTH_MILLIMETER, '1 m'],
|
||||
@@ -812,7 +812,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Pressure', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[45, UniversalYAxisUnit.PRESSURE_MILLIBAR, '45 mbar'],
|
||||
[1013, UniversalYAxisUnit.PRESSURE_MILLIBAR, '1.01 bar'],
|
||||
[27, UniversalYAxisUnit.PRESSURE_BAR, '27 bar'],
|
||||
@@ -828,7 +828,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Radiation', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[452, UniversalYAxisUnit.RADIATION_BECQUEREL, '452 Bq'],
|
||||
[37, UniversalYAxisUnit.RADIATION_CURIE, '37 Ci'],
|
||||
[128, UniversalYAxisUnit.RADIATION_GRAY, '128 Gy'],
|
||||
@@ -849,7 +849,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Rotation Speed', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[345, UniversalYAxisUnit.ROTATION_SPEED_REVOLUTIONS_PER_MINUTE, '345 rpm'],
|
||||
[789, UniversalYAxisUnit.ROTATION_SPEED_HERTZ, '789 Hz'],
|
||||
[789000, UniversalYAxisUnit.ROTATION_SPEED_HERTZ, '789 kHz'],
|
||||
@@ -861,7 +861,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Temperature', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[37, UniversalYAxisUnit.TEMPERATURE_CELSIUS, '37 °C'],
|
||||
[451, UniversalYAxisUnit.TEMPERATURE_FAHRENHEIT, '451 °F'],
|
||||
[310, UniversalYAxisUnit.TEMPERATURE_KELVIN, '310 K'],
|
||||
@@ -871,7 +871,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Velocity', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[900, UniversalYAxisUnit.VELOCITY_METERS_PER_SECOND, '900 m/s'],
|
||||
[456, UniversalYAxisUnit.VELOCITY_KILOMETERS_PER_HOUR, '456 km/h'],
|
||||
[789, UniversalYAxisUnit.VELOCITY_MILES_PER_HOUR, '789 mph'],
|
||||
@@ -882,7 +882,7 @@ describe('formatUniversalUnit', () => {
|
||||
});
|
||||
|
||||
describe('Volume', () => {
|
||||
test.each([
|
||||
it.each([
|
||||
[1200, UniversalYAxisUnit.VOLUME_MILLILITER, '1.2 L'],
|
||||
[9000000, UniversalYAxisUnit.VOLUME_MILLILITER, '9 kL'],
|
||||
[9, UniversalYAxisUnit.VOLUME_LITER, '9 L'],
|
||||
|
||||
@@ -16,8 +16,8 @@ describe('YAxisUnitSelector utils', () => {
|
||||
|
||||
it('returns null or self for unknown units', () => {
|
||||
expect(mapMetricUnitToUniversalUnit('unknown_unit')).toBe('unknown_unit');
|
||||
expect(mapMetricUnitToUniversalUnit('')).toBe(null);
|
||||
expect(mapMetricUnitToUniversalUnit(undefined)).toBe(null);
|
||||
expect(mapMetricUnitToUniversalUnit('')).toBeNull();
|
||||
expect(mapMetricUnitToUniversalUnit(undefined)).toBeNull();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -62,7 +62,7 @@ describe('YAxisUnitSelector utils', () => {
|
||||
},
|
||||
];
|
||||
const mergedCategories = mergeCategories(categories1, categories2);
|
||||
expect(mergedCategories).toEqual([
|
||||
expect(mergedCategories).toStrictEqual([
|
||||
{
|
||||
name: YAxisCategoryNames.Data,
|
||||
units: [
|
||||
|
||||
@@ -149,7 +149,7 @@ describe('CmdKPalette', () => {
|
||||
jest.clearAllMocks();
|
||||
});
|
||||
|
||||
test('renders navigation and settings groups and items', () => {
|
||||
it('renders navigation and settings groups and items', () => {
|
||||
render(<CmdKPalette userRole="ADMIN" />);
|
||||
|
||||
expect(screen.getByText('Navigation')).toBeInTheDocument();
|
||||
@@ -160,7 +160,7 @@ describe('CmdKPalette', () => {
|
||||
expect(screen.getByText('Switch to Dark Mode')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('clicking a navigation item calls history.push with correct route', async () => {
|
||||
it('clicking a navigation item calls history.push with correct route', async () => {
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<CmdKPalette userRole="ADMIN" />);
|
||||
|
||||
@@ -170,14 +170,14 @@ describe('CmdKPalette', () => {
|
||||
expect(history.push).toHaveBeenCalledWith(ROUTES.HOME);
|
||||
});
|
||||
|
||||
test('role-based filtering (basic smoke)', () => {
|
||||
it('role-based filtering (basic smoke)', () => {
|
||||
render(<CmdKPalette userRole="VIEWER" />);
|
||||
|
||||
// VIEWER still sees basic navigation items
|
||||
expect(screen.getByText(HOME_LABEL)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('keyboard shortcut opens palette via setOpen', () => {
|
||||
it('keyboard shortcut opens palette via setOpen', () => {
|
||||
render(<CmdKPalette userRole="ADMIN" />);
|
||||
|
||||
const event = new KeyboardEvent('keydown', { key: 'k', ctrlKey: true });
|
||||
@@ -186,7 +186,7 @@ describe('CmdKPalette', () => {
|
||||
expect(mockSetOpen).toHaveBeenCalledWith(true);
|
||||
});
|
||||
|
||||
test('items render with icons when provided', () => {
|
||||
it('items render with icons when provided', () => {
|
||||
render(<CmdKPalette userRole="ADMIN" />);
|
||||
|
||||
const iconHolders = document.querySelectorAll('.cmd-item-icon');
|
||||
@@ -194,7 +194,7 @@ describe('CmdKPalette', () => {
|
||||
expect(screen.getByText(HOME_LABEL)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('closing the palette via handleInvoke sets open to false', async () => {
|
||||
it('closing the palette via handleInvoke sets open to false', async () => {
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<CmdKPalette userRole="ADMIN" />);
|
||||
|
||||
|
||||
@@ -34,13 +34,13 @@ describe('Alert Channels Settings List page', () => {
|
||||
jest.useRealTimers();
|
||||
});
|
||||
describe('Should display the Alert Channels page properly', () => {
|
||||
it('Should check if "The alerts will be sent to all the configured channels." is visible ', () => {
|
||||
it('Should check if "The alerts will be sent to all the configured channels." is visible', () => {
|
||||
expect(screen.getByText('sending_channels_note')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if "New Alert Channel" Button is visble ', () => {
|
||||
it('Should check if "New Alert Channel" Button is visble', () => {
|
||||
expect(screen.getByText('button_new_channel')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if the help icon is visible and displays "tooltip_notification_channels ', async () => {
|
||||
it('Should check if the help icon is visible and displays "tooltip_notification_channels', async () => {
|
||||
const helpIcon = screen.getByLabelText('question-circle');
|
||||
|
||||
fireEvent.mouseOver(helpIcon);
|
||||
|
||||
@@ -38,7 +38,7 @@ describe('Alert Channels Settings List page (Normal User)', () => {
|
||||
jest.useRealTimers();
|
||||
});
|
||||
describe('Should display the Alert Channels page properly', () => {
|
||||
it('Should check if "The alerts will be sent to all the configured channels." is visible ', async () => {
|
||||
it('Should check if "The alerts will be sent to all the configured channels." is visible', async () => {
|
||||
await waitFor(() =>
|
||||
expect(screen.getByText('sending_channels_note')).toBeInTheDocument(),
|
||||
);
|
||||
@@ -51,7 +51,7 @@ describe('Alert Channels Settings List page (Normal User)', () => {
|
||||
await waitFor(() => expect(newAlertButton).toBeInTheDocument());
|
||||
expect(newAlertButton).toBeDisabled();
|
||||
});
|
||||
it('Should check if the help icon is visible and displays "tooltip_notification_channels ', async () => {
|
||||
it('Should check if the help icon is visible and displays "tooltip_notification_channels', async () => {
|
||||
const helpIcon = screen.getByLabelText('question-circle');
|
||||
fireEvent.mouseOver(helpIcon);
|
||||
|
||||
|
||||
@@ -44,7 +44,7 @@ describe('Create Alert Channel', () => {
|
||||
afterEach(() => {
|
||||
jest.clearAllMocks();
|
||||
});
|
||||
describe('Should check if the new alert channel is properly displayed with the cascading fields of slack channel ', () => {
|
||||
describe('Should check if the new alert channel is properly displayed with the cascading fields of slack channel', () => {
|
||||
beforeEach(() => {
|
||||
render(<CreateAlertChannels preType={ChannelType.Slack} />);
|
||||
});
|
||||
@@ -54,13 +54,13 @@ describe('Create Alert Channel', () => {
|
||||
it('Should check if the title is "New Notification Channels"', () => {
|
||||
expect(screen.getByText('page_title_create')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if the name label and textbox are displayed properly ', () => {
|
||||
it('Should check if the name label and textbox are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_channel_name',
|
||||
testId: 'channel-name-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly ', () => {
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_send_resolved',
|
||||
testId: 'field-send-resolved-checkbox',
|
||||
@@ -76,13 +76,13 @@ describe('Create Alert Channel', () => {
|
||||
it('Should check if the selected item in the type dropdown has text "Slack"', () => {
|
||||
expect(screen.getByText('Slack')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Recepient label, input, and help text are displayed properly ', () => {
|
||||
it('Should check if Recepient label, input, and help text are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_recipient',
|
||||
testId: 'slack-channel-textbox',
|
||||
@@ -90,7 +90,7 @@ describe('Create Alert Channel', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Title label and text area are displayed properly ', () => {
|
||||
it('Should check if Title label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_title',
|
||||
testId: 'title-textarea',
|
||||
@@ -101,7 +101,7 @@ describe('Create Alert Channel', () => {
|
||||
|
||||
expect(titleTextArea).toHaveTextContent(slackTitleDefaultValue);
|
||||
});
|
||||
it('Should check if Description label and text area are displayed properly ', () => {
|
||||
it('Should check if Description label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_description',
|
||||
testId: 'description-textarea',
|
||||
@@ -177,13 +177,13 @@ describe('Create Alert Channel', () => {
|
||||
it('Should check if the selected item in the type dropdown has text "Webhook"', () => {
|
||||
expect(screen.getByText('Webhook')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Webhook User Name label, input, and help text are displayed properly ', () => {
|
||||
it('Should check if Webhook User Name label, input, and help text are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_username',
|
||||
testId: 'webhook-username-textbox',
|
||||
@@ -321,7 +321,7 @@ describe('Create Alert Channel', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Message contains the default template ', () => {
|
||||
it('Should check if Message contains the default template', () => {
|
||||
const messageTextArea = screen.getByTestId('opsgenie-message-textarea');
|
||||
|
||||
expect(messageTextArea).toHaveValue(opsGenieMessageDefaultValue);
|
||||
@@ -387,14 +387,14 @@ describe('Create Alert Channel', () => {
|
||||
expect(screen.getByText('Microsoft Teams')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Title label and text area are displayed properly ', () => {
|
||||
it('Should check if Title label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_title',
|
||||
testId: 'title-textarea',
|
||||
@@ -406,7 +406,7 @@ describe('Create Alert Channel', () => {
|
||||
|
||||
expect(titleTextArea).toHaveTextContent(slackTitleDefaultValue);
|
||||
});
|
||||
it('Should check if Description label and text area are displayed properly ', () => {
|
||||
it('Should check if Description label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_description',
|
||||
testId: 'description-textarea',
|
||||
|
||||
@@ -23,20 +23,20 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
afterEach(() => {
|
||||
jest.clearAllMocks();
|
||||
});
|
||||
describe('Should check if the new alert channel is properly displayed with the cascading fields of slack channel ', () => {
|
||||
describe('Should check if the new alert channel is properly displayed with the cascading fields of slack channel', () => {
|
||||
beforeEach(() => {
|
||||
render(<CreateAlertChannels preType={ChannelType.Slack} />);
|
||||
});
|
||||
it('Should check if the title is "New Notification Channels"', () => {
|
||||
expect(screen.getByText('page_title_create')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if the name label and textbox are displayed properly ', () => {
|
||||
it('Should check if the name label and textbox are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_channel_name',
|
||||
testId: 'channel-name-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly ', () => {
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_send_resolved',
|
||||
testId: 'field-send-resolved-checkbox',
|
||||
@@ -52,13 +52,13 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
it('Should check if the selected item in the type dropdown has text "Slack"', () => {
|
||||
expect(screen.getByText('Slack')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Recepient label, input, and help text are displayed properly ', () => {
|
||||
it('Should check if Recepient label, input, and help text are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_recipient',
|
||||
testId: 'slack-channel-textbox',
|
||||
@@ -66,7 +66,7 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Title label and text area are displayed properly ', () => {
|
||||
it('Should check if Title label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_title',
|
||||
testId: 'title-textarea',
|
||||
@@ -77,7 +77,7 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
|
||||
expect(titleTextArea).toHaveTextContent(slackTitleDefaultValue);
|
||||
});
|
||||
it('Should check if Description label and text area are displayed properly ', () => {
|
||||
it('Should check if Description label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_description',
|
||||
testId: 'description-textarea',
|
||||
@@ -103,13 +103,13 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
it('Should check if the selected item in the type dropdown has text "Webhook"', () => {
|
||||
expect(screen.getByText('Webhook')).toBeInTheDocument();
|
||||
});
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
});
|
||||
});
|
||||
it('Should check if Webhook User Name label, input, and help text are displayed properly ', () => {
|
||||
it('Should check if Webhook User Name label, input, and help text are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_username',
|
||||
testId: 'webhook-username-textbox',
|
||||
@@ -247,7 +247,7 @@ describe('Create Alert Channel (Normal User)', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Message contains the default template ', () => {
|
||||
it('Should check if Message contains the default template', () => {
|
||||
const messageTextArea = screen.getByTestId('opsgenie-message-textarea');
|
||||
|
||||
expect(messageTextArea).toHaveValue(opsGenieMessageDefaultValue);
|
||||
|
||||
@@ -24,7 +24,7 @@ jest.mock('components/MarkdownRenderer/MarkdownRenderer', () => ({
|
||||
MarkdownRenderer: jest.fn(() => <div>Mocked MarkdownRenderer</div>),
|
||||
}));
|
||||
|
||||
describe('Should check if the edit alert channel is properly displayed ', () => {
|
||||
describe('Should check if the edit alert channel is properly displayed', () => {
|
||||
beforeEach(() => {
|
||||
render(<EditAlertChannels initialValue={editAlertChannelInitialValue} />);
|
||||
});
|
||||
@@ -35,14 +35,14 @@ describe('Should check if the edit alert channel is properly displayed ', () =>
|
||||
expect(screen.getByText('page_title_edit')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('Should check if the name label and textbox are displayed properly ', () => {
|
||||
it('Should check if the name label and textbox are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_channel_name',
|
||||
testId: 'channel-name-textbox',
|
||||
value: 'Dummy-Channel',
|
||||
});
|
||||
});
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly and the checkbox is checked ', () => {
|
||||
it('Should check if Send resolved alerts label and checkbox are displayed properly and the checkbox is checked', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_send_resolved',
|
||||
testId: 'field-send-resolved-checkbox',
|
||||
@@ -61,7 +61,7 @@ describe('Should check if the edit alert channel is properly displayed ', () =>
|
||||
expect(screen.getByText('Slack')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('Should check if Webhook URL label and input are displayed properly ', () => {
|
||||
it('Should check if Webhook URL label and input are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_webhook_url',
|
||||
testId: 'webhook-url-textbox',
|
||||
@@ -70,7 +70,7 @@ describe('Should check if the edit alert channel is properly displayed ', () =>
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Recepient label, input, and help text are displayed properly ', () => {
|
||||
it('Should check if Recepient label, input, and help text are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_recipient',
|
||||
testId: 'slack-channel-textbox',
|
||||
@@ -79,7 +79,7 @@ describe('Should check if the edit alert channel is properly displayed ', () =>
|
||||
});
|
||||
});
|
||||
|
||||
it('Should check if Title label and text area are displayed properly ', () => {
|
||||
it('Should check if Title label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_title',
|
||||
testId: 'title-textarea',
|
||||
@@ -92,7 +92,7 @@ describe('Should check if the edit alert channel is properly displayed ', () =>
|
||||
expect(titleTextArea).toHaveTextContent(slackTitleDefaultValue);
|
||||
});
|
||||
|
||||
it('Should check if Description label and text area are displayed properly ', () => {
|
||||
it('Should check if Description label and text area are displayed properly', () => {
|
||||
testLabelInputAndHelpValue({
|
||||
labelText: 'field_slack_description',
|
||||
testId: 'description-textarea',
|
||||
|
||||
@@ -12,7 +12,7 @@ import {
|
||||
} from './utils';
|
||||
|
||||
describe('Error utils', () => {
|
||||
test('Valid OrderBy Params', () => {
|
||||
it('Valid OrderBy Params', () => {
|
||||
expect(isOrderParams('serviceName')).toBe(true);
|
||||
expect(isOrderParams('exceptionCount')).toBe(true);
|
||||
expect(isOrderParams('lastSeen')).toBe(true);
|
||||
@@ -20,24 +20,24 @@ describe('Error utils', () => {
|
||||
expect(isOrderParams('exceptionType')).toBe(true);
|
||||
});
|
||||
|
||||
test('Invalid OrderBy Params', () => {
|
||||
it('Invalid OrderBy Params', () => {
|
||||
expect(isOrderParams('invalid')).toBe(false);
|
||||
expect(isOrderParams(null)).toBe(false);
|
||||
expect(isOrderParams('')).toBe(false);
|
||||
});
|
||||
|
||||
test('Valid Order', () => {
|
||||
it('Valid Order', () => {
|
||||
expect(isOrder('ascending')).toBe(true);
|
||||
expect(isOrder('descending')).toBe(true);
|
||||
});
|
||||
|
||||
test('Invalid Order', () => {
|
||||
it('Invalid Order', () => {
|
||||
expect(isOrder('invalid')).toBe(false);
|
||||
expect(isOrder(null)).toBe(false);
|
||||
expect(isOrder('')).toBe(false);
|
||||
});
|
||||
|
||||
test('Default Order', () => {
|
||||
it('Default Order', () => {
|
||||
const OrderBy: OrderBy[] = [
|
||||
'exceptionCount',
|
||||
'exceptionType',
|
||||
@@ -57,7 +57,7 @@ describe('Error utils', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('Limit', () => {
|
||||
it('Limit', () => {
|
||||
expect(getLimit(null)).toBe(10);
|
||||
expect(getLimit('')).toBe(10);
|
||||
expect(getLimit('0')).toBe(0);
|
||||
@@ -68,7 +68,7 @@ describe('Error utils', () => {
|
||||
expect(getLimit('101')).toBe(101);
|
||||
});
|
||||
|
||||
test('Update Page Size', () => {
|
||||
it('Update Page Size', () => {
|
||||
expect(getUpdatePageSize(null)).toBe(10);
|
||||
expect(getUpdatePageSize('')).toBe(10);
|
||||
expect(getUpdatePageSize('0')).toBe(0);
|
||||
@@ -79,7 +79,7 @@ describe('Error utils', () => {
|
||||
expect(getUpdatePageSize('101')).toBe(101);
|
||||
});
|
||||
|
||||
test('Order Params', () => {
|
||||
it('Order Params', () => {
|
||||
expect(getOrderParams(null)).toBe('serviceName');
|
||||
expect(getOrderParams('')).toBe('serviceName');
|
||||
expect(getOrderParams('serviceName')).toBe('serviceName');
|
||||
@@ -89,7 +89,7 @@ describe('Error utils', () => {
|
||||
expect(getOrderParams('exceptionType')).toBe('exceptionType');
|
||||
});
|
||||
|
||||
test('OffSet', () => {
|
||||
it('OffSet', () => {
|
||||
expect(getOffSet(null)).toBe(0);
|
||||
expect(getOffSet('')).toBe(0);
|
||||
expect(getOffSet('0')).toBe(0);
|
||||
@@ -100,7 +100,7 @@ describe('Error utils', () => {
|
||||
expect(getOffSet('101')).toBe(101);
|
||||
});
|
||||
|
||||
test('Order', () => {
|
||||
it('Order', () => {
|
||||
expect(getOrder(null)).toBe('ascending');
|
||||
expect(getOrder('')).toBe('ascending');
|
||||
expect(getOrder('ascending')).toBe('ascending');
|
||||
|
||||
@@ -30,18 +30,18 @@ function UplotChart({
|
||||
|
||||
useEffect(() => {
|
||||
if (plotInstance.current) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
plotInstance.current.destroy();
|
||||
}
|
||||
|
||||
if (data && data.length > 0) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
plotInstance.current = new uPlot(options, data, chartRef.current);
|
||||
}
|
||||
|
||||
return (): void => {
|
||||
if (plotInstance.current) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
plotInstance.current.destroy();
|
||||
}
|
||||
};
|
||||
@@ -275,7 +275,7 @@ function AnomalyAlertEvaluationView({
|
||||
};
|
||||
|
||||
const handleSearchValueChange = useDebouncedFn((event): void => {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
const value = event?.target?.value || '';
|
||||
|
||||
handleSearch(value);
|
||||
|
||||
@@ -233,7 +233,7 @@ describe('DomainMetrics - V5 Query Payload Tests', () => {
|
||||
// Wait for skeletons to disappear
|
||||
await waitFor(() => {
|
||||
const skeletons = document.querySelectorAll('.ant-skeleton-button');
|
||||
expect(skeletons.length).toBe(0);
|
||||
expect(skeletons).toHaveLength(0);
|
||||
});
|
||||
|
||||
// Verify all metric labels are displayed
|
||||
@@ -272,7 +272,7 @@ describe('DomainMetrics - V5 Query Payload Tests', () => {
|
||||
|
||||
await waitFor(() => {
|
||||
const skeletons = document.querySelectorAll('.ant-skeleton-button');
|
||||
expect(skeletons.length).toBe(0);
|
||||
expect(skeletons).toHaveLength(0);
|
||||
});
|
||||
|
||||
// When no data, all values should show "-"
|
||||
|
||||
@@ -303,7 +303,7 @@ describe('EndPointMetrics - V5 Query Payload Tests', () => {
|
||||
// Wait for skeletons to disappear
|
||||
await waitFor(() => {
|
||||
const skeletons = document.querySelectorAll('.ant-skeleton-button');
|
||||
expect(skeletons.length).toBe(0);
|
||||
expect(skeletons).toHaveLength(0);
|
||||
});
|
||||
|
||||
// Verify all metric labels are displayed
|
||||
@@ -342,7 +342,7 @@ describe('EndPointMetrics - V5 Query Payload Tests', () => {
|
||||
|
||||
await waitFor(() => {
|
||||
const skeletons = document.querySelectorAll('.ant-skeleton-button');
|
||||
expect(skeletons.length).toBe(0);
|
||||
expect(skeletons).toHaveLength(0);
|
||||
});
|
||||
|
||||
// When no data, all values should show "-"
|
||||
|
||||
@@ -303,7 +303,7 @@ describe('API Monitoring Utils', () => {
|
||||
const result = extractPortAndEndpoint(url);
|
||||
|
||||
// Assert
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
port: '8080',
|
||||
endpoint: '/api/endpoint?param=value',
|
||||
});
|
||||
@@ -317,7 +317,7 @@ describe('API Monitoring Utils', () => {
|
||||
const result = extractPortAndEndpoint(url);
|
||||
|
||||
// Assert
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
port: '-',
|
||||
endpoint: '/api/endpoint',
|
||||
});
|
||||
@@ -331,7 +331,7 @@ describe('API Monitoring Utils', () => {
|
||||
const result = extractPortAndEndpoint(nonUrl);
|
||||
|
||||
// Assert
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
port: '-',
|
||||
endpoint: nonUrl,
|
||||
});
|
||||
@@ -379,7 +379,7 @@ describe('API Monitoring Utils', () => {
|
||||
const result = getFormattedEndPointDropDownData([]);
|
||||
|
||||
// Assert
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle undefined input', () => {
|
||||
@@ -392,7 +392,7 @@ describe('API Monitoring Utils', () => {
|
||||
// Assert
|
||||
// If the implementation doesn't handle undefined, just check that it returns something predictable
|
||||
// Based on the error, it seems the function returns undefined for undefined input
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle items without URL path', () => {
|
||||
@@ -460,7 +460,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(2);
|
||||
expect(result).toHaveLength(2);
|
||||
|
||||
// Check first item
|
||||
expect(result[0].statusCode).toBe('200');
|
||||
@@ -493,7 +493,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(1);
|
||||
expect(result).toHaveLength(1);
|
||||
expect(result[0].statusCode).toBe('-');
|
||||
expect(result[0].count).toBe('-');
|
||||
expect(result[0].p99Latency).toBe('-');
|
||||
@@ -506,7 +506,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle undefined input', () => {
|
||||
@@ -518,7 +518,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle mixed status code formats and preserve order', () => {
|
||||
@@ -555,7 +555,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(3);
|
||||
expect(result).toHaveLength(3);
|
||||
|
||||
// Check order preservation - should maintain the same order as input
|
||||
expect(result[0].statusCode).toBe('404');
|
||||
@@ -675,7 +675,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.data.result).toEqual([]);
|
||||
expect(result.data.result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle empty result array', () => {
|
||||
@@ -695,7 +695,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.data.result).toEqual([]);
|
||||
expect(result.data.result).toStrictEqual([]);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -779,7 +779,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(2);
|
||||
expect(result).toHaveLength(2);
|
||||
|
||||
// Should have two filters, one for >= start code and one for <= end code
|
||||
const startRangeFilter = result.find((item) => item.op === '>=');
|
||||
@@ -811,7 +811,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(2);
|
||||
expect(result).toHaveLength(2);
|
||||
|
||||
const startRangeFilter = result.find((item) => item.op === '>=');
|
||||
const endRangeFilter = result.find((item) => item.op === '<=');
|
||||
@@ -832,7 +832,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle empty metric object', () => {
|
||||
@@ -841,7 +841,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle metric without response_status_code', () => {
|
||||
@@ -855,7 +855,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result).toEqual([]);
|
||||
expect(result).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle unsupported status code range', () => {
|
||||
@@ -869,7 +869,7 @@ describe('API Monitoring Utils', () => {
|
||||
|
||||
// Assert
|
||||
expect(result).toBeDefined();
|
||||
expect(result.length).toBe(2);
|
||||
expect(result).toHaveLength(2);
|
||||
|
||||
// Should still have two filters
|
||||
const startRangeFilter = result.find((item) => item.op === '>=');
|
||||
|
||||
@@ -61,25 +61,29 @@ describe('AllEndpointsWidget - V5 Migration Validation', () => {
|
||||
// Query A: count()
|
||||
expect(queryA.aggregations).toBeDefined();
|
||||
expect(Array.isArray(queryA.aggregations)).toBe(true);
|
||||
expect(queryA.aggregations).toEqual([{ expression: 'count()' }]);
|
||||
expect(queryA.aggregations).toStrictEqual([{ expression: 'count()' }]);
|
||||
expect(queryA).not.toHaveProperty('aggregateAttribute');
|
||||
|
||||
// Query B: p99(duration_nano)
|
||||
expect(queryB.aggregations).toBeDefined();
|
||||
expect(Array.isArray(queryB.aggregations)).toBe(true);
|
||||
expect(queryB.aggregations).toEqual([{ expression: 'p99(duration_nano)' }]);
|
||||
expect(queryB.aggregations).toStrictEqual([
|
||||
{ expression: 'p99(duration_nano)' },
|
||||
]);
|
||||
expect(queryB).not.toHaveProperty('aggregateAttribute');
|
||||
|
||||
// Query C: max(timestamp)
|
||||
expect(queryC.aggregations).toBeDefined();
|
||||
expect(Array.isArray(queryC.aggregations)).toBe(true);
|
||||
expect(queryC.aggregations).toEqual([{ expression: 'max(timestamp)' }]);
|
||||
expect(queryC.aggregations).toStrictEqual([
|
||||
{ expression: 'max(timestamp)' },
|
||||
]);
|
||||
expect(queryC).not.toHaveProperty('aggregateAttribute');
|
||||
|
||||
// Query D: count() (disabled, for errors)
|
||||
expect(queryD.aggregations).toBeDefined();
|
||||
expect(Array.isArray(queryD.aggregations)).toBe(true);
|
||||
expect(queryD.aggregations).toEqual([{ expression: 'count()' }]);
|
||||
expect(queryD.aggregations).toStrictEqual([{ expression: 'count()' }]);
|
||||
expect(queryD).not.toHaveProperty('aggregateAttribute');
|
||||
});
|
||||
|
||||
|
||||
@@ -60,7 +60,7 @@ describe('EndpointDropdown - V5 Migration Validation', () => {
|
||||
// V5 Aggregation format: aggregations array (not aggregateAttribute)
|
||||
expect(queryA.aggregations).toBeDefined();
|
||||
expect(Array.isArray(queryA.aggregations)).toBe(true);
|
||||
expect(queryA.aggregations?.[0]).toEqual({
|
||||
expect(queryA.aggregations?.[0]).toStrictEqual({
|
||||
expression: 'count()',
|
||||
});
|
||||
expect(queryA).not.toHaveProperty('aggregateAttribute');
|
||||
|
||||
@@ -19,7 +19,7 @@ describe('API Monitoring Query Params', () => {
|
||||
describe('getApiMonitoringParams', () => {
|
||||
it('returns default params when no query param exists', () => {
|
||||
const search = '';
|
||||
expect(getApiMonitoringParams(search)).toEqual(DEFAULT_PARAMS);
|
||||
expect(getApiMonitoringParams(search)).toStrictEqual(DEFAULT_PARAMS);
|
||||
});
|
||||
|
||||
it('parses URL query params correctly', () => {
|
||||
@@ -52,7 +52,7 @@ describe('API Monitoring Query Params', () => {
|
||||
urlParams.set('apiMonitoringParams', 'invalid-json');
|
||||
const search = `?${urlParams.toString()}`;
|
||||
|
||||
expect(getApiMonitoringParams(search)).toEqual(DEFAULT_PARAMS);
|
||||
expect(getApiMonitoringParams(search)).toStrictEqual(DEFAULT_PARAMS);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -4,13 +4,7 @@ import {
|
||||
notOfTrailResponse,
|
||||
trialConvertedToSubscriptionResponse,
|
||||
} from 'mocks-server/__mockdata__/licenses';
|
||||
import { act, render, screen, getAppContextMock } from 'tests/test-utils';
|
||||
import APIError from 'types/api/error';
|
||||
import {
|
||||
LicensePlatform,
|
||||
LicenseResModel,
|
||||
LicenseState,
|
||||
} from 'types/api/licensesV3/getActive';
|
||||
import { act, render, screen } from 'tests/test-utils';
|
||||
import { getFormattedDate } from 'utils/timeUtils';
|
||||
|
||||
import BillingContainer from './BillingContainer';
|
||||
@@ -105,10 +99,6 @@ describe('BillingContainer', () => {
|
||||
await expect(
|
||||
screen.findByRole('link', { name: /here/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
await expect(
|
||||
screen.findByText('Cancel Subscription', { selector: 'span' }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('OnTrail but trialConvertedToSubscription', async () => {
|
||||
@@ -148,85 +138,6 @@ describe('BillingContainer', () => {
|
||||
const dayRemainingInBillingPeriod =
|
||||
await screen.findByText(/1 days_remaining/i);
|
||||
expect(dayRemainingInBillingPeriod).toBeInTheDocument();
|
||||
|
||||
await expect(
|
||||
screen.findByText('Cancel Subscription', { selector: 'span' }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
describe('CancelSubscriptionBanner visibility', () => {
|
||||
const baseActiveLicense = getAppContextMock('ADMIN')
|
||||
.activeLicense as LicenseResModel;
|
||||
|
||||
it('should render when license is ACTIVATED and platform is CLOUD', async () => {
|
||||
render(<BillingContainer />);
|
||||
await expect(
|
||||
screen.findByText('Cancel Subscription', { selector: 'span' }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it.each([
|
||||
['EXPIRED', LicenseState.EXPIRED],
|
||||
['TERMINATED', LicenseState.TERMINATED],
|
||||
['CANCELLED', LicenseState.CANCELLED],
|
||||
['EVALUATION_EXPIRED', LicenseState.EVALUATION_EXPIRED],
|
||||
['DEFAULTED', LicenseState.DEFAULTED],
|
||||
['ISSUED', LicenseState.ISSUED],
|
||||
['EVALUATING', LicenseState.EVALUATING],
|
||||
])('should not render when license state is %s', async (_, state) => {
|
||||
render(
|
||||
<BillingContainer />,
|
||||
{},
|
||||
{
|
||||
appContextOverrides: {
|
||||
activeLicense: { ...baseActiveLicense, state },
|
||||
},
|
||||
},
|
||||
);
|
||||
await screen.findByText('billing');
|
||||
expect(
|
||||
screen.queryByText('Cancel Subscription', { selector: 'span' }),
|
||||
).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
const makeAPIError = (statusCode: number): APIError =>
|
||||
new APIError({
|
||||
httpStatusCode: statusCode as any,
|
||||
error: { code: 'error', message: 'error', url: '', errors: [] },
|
||||
});
|
||||
|
||||
it.each([
|
||||
[
|
||||
'Self-Hosted platform',
|
||||
{
|
||||
activeLicense: {
|
||||
...baseActiveLicense,
|
||||
platform: LicensePlatform.SELF_HOSTED,
|
||||
},
|
||||
activeLicenseFetchError: null,
|
||||
},
|
||||
],
|
||||
[
|
||||
'Community Enterprise user (license API 404)',
|
||||
{
|
||||
activeLicense: null,
|
||||
activeLicenseFetchError: makeAPIError(404),
|
||||
},
|
||||
],
|
||||
[
|
||||
'Community user (license API 501)',
|
||||
{
|
||||
activeLicense: null,
|
||||
activeLicenseFetchError: makeAPIError(501),
|
||||
},
|
||||
],
|
||||
])('should not render for %s', async (_, overrides) => {
|
||||
render(<BillingContainer />, {}, { appContextOverrides: overrides });
|
||||
await screen.findByText('billing');
|
||||
expect(
|
||||
screen.queryByText('Cancel Subscription', { selector: 'span' }),
|
||||
).not.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -34,12 +34,10 @@ import { CheckoutSuccessPayloadProps } from 'types/api/billing/checkout';
|
||||
import { getBaseUrl } from 'utils/basePath';
|
||||
import { getFormattedDate, getRemainingDays } from 'utils/timeUtils';
|
||||
|
||||
import CancelSubscriptionBanner from './CancelSubscriptionBanner';
|
||||
import { BillingUsageGraph } from './BillingUsageGraph/BillingUsageGraph';
|
||||
import { prepareCsvData } from './BillingUsageGraph/utils';
|
||||
|
||||
import './BillingContainer.styles.scss';
|
||||
import { LicenseState } from 'types/api/licensesV3/getActive';
|
||||
|
||||
interface DataType {
|
||||
key: string;
|
||||
@@ -319,7 +317,7 @@ export default function BillingContainer(): JSX.Element {
|
||||
|
||||
const handleBilling = useCallback(async () => {
|
||||
if (!trialInfo?.trialConvertedToSubscription) {
|
||||
void logEvent('Billing : Upgrade Plan', {
|
||||
logEvent('Billing : Upgrade Plan', {
|
||||
user: pick(user, ['email', 'userId', 'name']),
|
||||
org,
|
||||
});
|
||||
@@ -328,7 +326,7 @@ export default function BillingContainer(): JSX.Element {
|
||||
url: getBaseUrl(),
|
||||
});
|
||||
} else {
|
||||
void logEvent('Billing : Manage Billing', {
|
||||
logEvent('Billing : Manage Billing', {
|
||||
user: pick(user, ['email', 'userId', 'name']),
|
||||
org,
|
||||
});
|
||||
@@ -537,10 +535,6 @@ export default function BillingContainer(): JSX.Element {
|
||||
{(isLoading || isFetchingBillingData) && renderTableSkeleton()}
|
||||
</div>
|
||||
|
||||
{isCloudUserVal && activeLicense?.state === LicenseState.ACTIVATED && (
|
||||
<CancelSubscriptionBanner />
|
||||
)}
|
||||
|
||||
{!trialInfo?.trialConvertedToSubscription && (
|
||||
<div className="upgrade-plan-benefits">
|
||||
<Row
|
||||
|
||||
@@ -1,35 +0,0 @@
|
||||
.banner {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: var(--padding-4);
|
||||
border-radius: 4px;
|
||||
border: 1px solid var(--callout-error-border);
|
||||
background-color: var(--callout-error-background);
|
||||
margin: var(--spacing-4) 0 var(--spacing-12);
|
||||
}
|
||||
|
||||
.info {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: var(--spacing-2);
|
||||
}
|
||||
|
||||
.title {
|
||||
font-size: var(--font-size-sm);
|
||||
font-weight: var(--font-weight-medium);
|
||||
color: var(--callout-error-title);
|
||||
}
|
||||
|
||||
.subtitle {
|
||||
font-size: var(--paragraph-base-400-font-size);
|
||||
font-weight: var(--paragraph-base-400-font-weight);
|
||||
line-height: var(--paragraph-base-400-line-height);
|
||||
color: var(--callout-error-icon);
|
||||
}
|
||||
|
||||
.dialogBody {
|
||||
font-size: var(--font-size-sm);
|
||||
line-height: var(--line-height-relaxed);
|
||||
color: var(--l2-foreground);
|
||||
}
|
||||
@@ -1,68 +0,0 @@
|
||||
import { render, screen, userEvent } from 'tests/test-utils';
|
||||
|
||||
import CancelSubscriptionBanner from './CancelSubscriptionBanner';
|
||||
|
||||
jest.mock('utils/basePath', () => ({
|
||||
getBasePath: (): string => '/',
|
||||
withBasePath: (path: string): string => path,
|
||||
getAbsoluteUrl: (path: string): string => `https://test.signoz.io${path}`,
|
||||
getBaseUrl: (): string => 'https://test.signoz.io',
|
||||
}));
|
||||
|
||||
describe('CancelSubscriptionBanner', () => {
|
||||
it('renders banner with title and subtitle', () => {
|
||||
render(<CancelSubscriptionBanner />);
|
||||
expect(
|
||||
screen.getByText('Cancel Subscription', { selector: 'span' }),
|
||||
).toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByText('Cancel your SigNoz subscription.'),
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('opens dialog with correct content when Cancel Subscription is clicked', async () => {
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<CancelSubscriptionBanner />);
|
||||
|
||||
await user.click(
|
||||
screen.getByRole('button', { name: /cancel subscription/i }),
|
||||
);
|
||||
|
||||
expect(screen.getByRole('dialog')).toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByText(/reach out to our support team/i),
|
||||
).toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByRole('button', { name: /keep subscription/i }),
|
||||
).toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByRole('button', { name: /contact support/i }),
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('sends mailto to cloud-support with correct subject on Contact Support', async () => {
|
||||
const realCreateElement = document.createElement.bind(document);
|
||||
const mockClick = jest.fn();
|
||||
const mockAnchor = { href: '', click: mockClick };
|
||||
jest.spyOn(document, 'createElement').mockImplementation((tag: string) => {
|
||||
if (tag === 'a') {
|
||||
return mockAnchor as unknown as HTMLAnchorElement;
|
||||
}
|
||||
return realCreateElement(tag);
|
||||
});
|
||||
|
||||
const user = userEvent.setup({ pointerEventsCheck: 0 });
|
||||
render(<CancelSubscriptionBanner />);
|
||||
|
||||
await user.click(
|
||||
screen.getByRole('button', { name: /cancel subscription/i }),
|
||||
);
|
||||
await user.click(screen.getByRole('button', { name: /contact support/i }));
|
||||
|
||||
expect(mockAnchor.href).toContain('mailto:cloud-support@signoz.io');
|
||||
expect(mockAnchor.href).toContain('Cancel%20My%20SigNoz%20Subscription');
|
||||
expect(mockClick).toHaveBeenCalledTimes(1);
|
||||
|
||||
jest.restoreAllMocks();
|
||||
});
|
||||
});
|
||||
@@ -1,106 +0,0 @@
|
||||
import { useState } from 'react';
|
||||
import { X } from '@signozhq/icons';
|
||||
import { Button, DialogWrapper } from '@signozhq/ui';
|
||||
import logEvent from 'api/common/logEvent';
|
||||
import { pick } from 'lodash-es';
|
||||
import { useAppContext } from 'providers/App/App';
|
||||
import { getBaseUrl } from 'utils/basePath';
|
||||
|
||||
import styles from './CancelSubscriptionBanner.module.scss';
|
||||
|
||||
function CancelSubscriptionBanner(): JSX.Element {
|
||||
const [open, setOpen] = useState(false);
|
||||
const { user, org } = useAppContext();
|
||||
|
||||
const handleOpenCancelDialog = (): void => {
|
||||
void logEvent('Billing : Cancel Subscription Clicked', {
|
||||
user: pick(user, ['email', 'displayName', 'role', 'organization']),
|
||||
role: user?.role,
|
||||
});
|
||||
setOpen(true);
|
||||
};
|
||||
|
||||
const handleContactSupport = (): void => {
|
||||
void logEvent('Billing : Cancel Subscription Confirmed', {
|
||||
user: pick(user, ['email', 'displayName', 'role', 'organization']),
|
||||
role: user?.role,
|
||||
});
|
||||
const subject = encodeURIComponent('Cancel My SigNoz Subscription');
|
||||
const orgName = org?.[0]?.displayName ?? '';
|
||||
const body = encodeURIComponent(
|
||||
[
|
||||
'Hi SigNoz Team,',
|
||||
'',
|
||||
'I would like to cancel my SigNoz Cloud subscription.',
|
||||
'Please find my account details below.',
|
||||
'',
|
||||
'Account Details:',
|
||||
` • SigNoz URL: ${getBaseUrl()}`,
|
||||
...(orgName ? [` • Organization: ${orgName}`] : []),
|
||||
` • Account Email: ${user?.email ?? ''}`,
|
||||
'',
|
||||
'Reason for Cancellation:',
|
||||
'[Please share the reason for cancellation]',
|
||||
'',
|
||||
'Additional feedback (optional):',
|
||||
'[Any other feedback]',
|
||||
'',
|
||||
'Regards,',
|
||||
'[user name or team name]',
|
||||
].join('\n'),
|
||||
);
|
||||
const link = document.createElement('a');
|
||||
link.href = `mailto:cloud-support@signoz.io?subject=${subject}&body=${body}`;
|
||||
link.click();
|
||||
setOpen(false);
|
||||
};
|
||||
|
||||
const footer = (
|
||||
<>
|
||||
<Button
|
||||
variant="solid"
|
||||
color="secondary"
|
||||
onClick={(): void => setOpen(false)}
|
||||
>
|
||||
Keep Subscription
|
||||
</Button>
|
||||
<Button variant="solid" color="destructive" onClick={handleContactSupport}>
|
||||
Contact Support
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className={styles.banner}>
|
||||
<div className={styles.info}>
|
||||
<span className={styles.title}>Cancel Subscription</span>
|
||||
<span className={styles.subtitle}>Cancel your SigNoz subscription.</span>
|
||||
</div>
|
||||
<Button
|
||||
variant="solid"
|
||||
color="destructive"
|
||||
prefix={<X size={12} />}
|
||||
onClick={handleOpenCancelDialog}
|
||||
>
|
||||
Cancel Subscription
|
||||
</Button>
|
||||
</div>
|
||||
<DialogWrapper
|
||||
open={open}
|
||||
onOpenChange={setOpen}
|
||||
title="Cancel your subscription"
|
||||
width="narrow"
|
||||
showCloseButton
|
||||
footer={footer}
|
||||
>
|
||||
<p className={styles.dialogBody}>
|
||||
To cancel your SigNoz subscription, please reach out to our support team.
|
||||
We'll be happy to assist you.
|
||||
</p>
|
||||
</DialogWrapper>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
export default CancelSubscriptionBanner;
|
||||
@@ -242,7 +242,7 @@ describe('utils', () => {
|
||||
);
|
||||
|
||||
expect(rrulestr).toHaveBeenCalledWith(FREQ_DAILY);
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
new Date(MOCK_DATE_STRING),
|
||||
new Date('2024-01-16T10:30:00Z'),
|
||||
new Date('2024-01-17T10:30:00Z'),
|
||||
@@ -300,7 +300,7 @@ describe('utils', () => {
|
||||
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 10:30:00',
|
||||
'01-02-2024 10:30:00',
|
||||
'15-02-2024 10:30:00',
|
||||
@@ -319,7 +319,7 @@ describe('utils', () => {
|
||||
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 12:30:00',
|
||||
'19-01-2024 12:30:00',
|
||||
'22-01-2024 12:30:00',
|
||||
@@ -339,7 +339,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today included (15-01-2024 00:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 10:30:00',
|
||||
'19-01-2024 10:30:00',
|
||||
'22-01-2024 10:30:00',
|
||||
@@ -359,7 +359,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today excluded (15-01-2024 00:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'19-01-2024 00:00:00',
|
||||
'22-01-2024 00:00:00',
|
||||
'26-01-2024 00:00:00',
|
||||
@@ -379,7 +379,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today excluded (15-01-2024 00:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'19-01-2024 00:30:00',
|
||||
'22-01-2024 00:30:00',
|
||||
'26-01-2024 00:30:00',
|
||||
@@ -398,7 +398,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today included (15-01-2024 10:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 10:30:00',
|
||||
'15-02-2024 10:30:00',
|
||||
'15-03-2024 10:30:00',
|
||||
@@ -417,7 +417,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today excluded (15-01-2024 10:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-02-2024 00:00:00',
|
||||
'15-03-2024 00:00:00',
|
||||
'15-04-2024 00:00:00',
|
||||
@@ -436,7 +436,7 @@ describe('utils', () => {
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
// today excluded (15-01-2024 10:30:00)
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-02-2024 00:30:00',
|
||||
'15-03-2024 00:30:00',
|
||||
'15-04-2024 00:30:00',
|
||||
@@ -455,7 +455,7 @@ describe('utils', () => {
|
||||
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'29-01-2024 10:30:00',
|
||||
'29-02-2024 10:30:00',
|
||||
'29-03-2024 10:30:00',
|
||||
@@ -474,7 +474,7 @@ describe('utils', () => {
|
||||
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'31-01-2024 10:30:00',
|
||||
'31-03-2024 10:30:00',
|
||||
'31-05-2024 10:30:00',
|
||||
@@ -511,7 +511,7 @@ describe('utils', () => {
|
||||
5,
|
||||
);
|
||||
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'29-01-2023 10:30:00',
|
||||
'29-03-2023 10:30:00',
|
||||
'29-04-2023 10:30:00',
|
||||
@@ -529,7 +529,7 @@ describe('utils', () => {
|
||||
);
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 10:40:00',
|
||||
'16-01-2024 10:40:00',
|
||||
'17-01-2024 10:40:00',
|
||||
@@ -547,7 +547,7 @@ describe('utils', () => {
|
||||
);
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'16-01-2024 00:00:00',
|
||||
'17-01-2024 00:00:00',
|
||||
'18-01-2024 00:00:00',
|
||||
@@ -565,7 +565,7 @@ describe('utils', () => {
|
||||
);
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'16-01-2024 00:30:00',
|
||||
'17-01-2024 00:30:00',
|
||||
'18-01-2024 00:30:00',
|
||||
@@ -583,7 +583,7 @@ describe('utils', () => {
|
||||
);
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'15-01-2024 10:30:00',
|
||||
'16-01-2024 10:30:00',
|
||||
'17-01-2024 10:30:00',
|
||||
@@ -621,7 +621,7 @@ describe('utils', () => {
|
||||
);
|
||||
expect(result).toBeDefined();
|
||||
expect(Array.isArray(result)).toBe(true);
|
||||
expect(result?.map((res) => formatDate(res))).toEqual([
|
||||
expect(result?.map((res) => formatDate(res))).toStrictEqual([
|
||||
'31-01-2024 10:30:00',
|
||||
'01-02-2024 10:30:00',
|
||||
'02-02-2024 10:30:00',
|
||||
|
||||
@@ -333,7 +333,7 @@ describe('QuerySection', () => {
|
||||
|
||||
const result = mockUseQueryBuilder.redirectWithQueryBuilderData.mock.calls[0];
|
||||
|
||||
expect(result[0]).toEqual({
|
||||
expect(result[0]).toStrictEqual({
|
||||
id: MOCK_UUID,
|
||||
queryType: EQueryType.QUERY_BUILDER,
|
||||
unit: undefined,
|
||||
@@ -351,7 +351,7 @@ describe('QuerySection', () => {
|
||||
clickhouse_sql: [initialClickHouseData],
|
||||
});
|
||||
|
||||
expect(result[1]).toEqual({
|
||||
expect(result[1]).toStrictEqual({
|
||||
[QueryParams.alertType]: AlertTypes.METRICS_BASED_ALERT,
|
||||
[QueryParams.ruleType]: AlertDetectionTypes.THRESHOLD_ALERT,
|
||||
});
|
||||
@@ -371,7 +371,7 @@ describe('QuerySection', () => {
|
||||
const [queryArg] =
|
||||
mockUseQueryBuilder.redirectWithQueryBuilderData.mock.calls[0];
|
||||
|
||||
expect(queryArg).toEqual({
|
||||
expect(queryArg).toStrictEqual({
|
||||
...mockUseQueryBuilder.currentQuery,
|
||||
queryType: EQueryType.PROM,
|
||||
});
|
||||
@@ -425,7 +425,7 @@ describe('QuerySection', () => {
|
||||
const [queryArg] =
|
||||
mockUseQueryBuilder.redirectWithQueryBuilderData.mock.calls[0];
|
||||
|
||||
expect(queryArg).toEqual({
|
||||
expect(queryArg).toStrictEqual({
|
||||
...mockCurrentQueryWithPromQL,
|
||||
queryType: EQueryType.QUERY_BUILDER,
|
||||
});
|
||||
@@ -479,7 +479,7 @@ describe('QuerySection', () => {
|
||||
const [queryArg] =
|
||||
mockUseQueryBuilder.redirectWithQueryBuilderData.mock.calls[0];
|
||||
|
||||
expect(queryArg).toEqual({
|
||||
expect(queryArg).toStrictEqual({
|
||||
...mockCurrentQueryWithClickhouseSQL,
|
||||
queryType: EQueryType.QUERY_BUILDER,
|
||||
});
|
||||
|
||||
@@ -54,7 +54,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_ALERT_NAME',
|
||||
payload: 'Test Alert',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_STATE,
|
||||
name: 'Test Alert',
|
||||
});
|
||||
@@ -66,7 +66,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_ALERT_LABELS',
|
||||
payload: labels,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_STATE,
|
||||
labels,
|
||||
});
|
||||
@@ -77,7 +77,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_Y_AXIS_UNIT',
|
||||
payload: 'ms',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_STATE,
|
||||
yAxisUnit: 'ms',
|
||||
});
|
||||
@@ -90,7 +90,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
yAxisUnit: 'ms',
|
||||
};
|
||||
const result = alertCreationReducer(modifiedState, { type: 'RESET' });
|
||||
expect(result).toEqual(INITIAL_ALERT_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ALERT_STATE);
|
||||
});
|
||||
|
||||
it(TEST_SET_INITIAL_STATE_FROM_PAYLOAD, () => {
|
||||
@@ -103,7 +103,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_INITIAL_STATE',
|
||||
payload: newState,
|
||||
});
|
||||
expect(result).toEqual(newState);
|
||||
expect(result).toStrictEqual(newState);
|
||||
});
|
||||
|
||||
it(TEST_RETURN_STATE_FOR_UNKNOWN_ACTION, () => {
|
||||
@@ -112,7 +112,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
|
||||
{ type: UNKNOWN_ACTION_TYPE } as any,
|
||||
);
|
||||
expect(result).toEqual(INITIAL_ALERT_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ALERT_STATE);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -211,7 +211,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_SELECTED_QUERY',
|
||||
payload: 'B',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_THRESHOLD_STATE,
|
||||
selectedQuery: 'B',
|
||||
});
|
||||
@@ -222,7 +222,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_OPERATOR',
|
||||
payload: AlertThresholdOperator.IS_BELOW,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_THRESHOLD_STATE,
|
||||
operator: AlertThresholdOperator.IS_BELOW,
|
||||
});
|
||||
@@ -233,7 +233,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_MATCH_TYPE',
|
||||
payload: AlertThresholdMatchType.ALL_THE_TIME,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_THRESHOLD_STATE,
|
||||
matchType: AlertThresholdMatchType.ALL_THE_TIME,
|
||||
});
|
||||
@@ -255,7 +255,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_THRESHOLDS',
|
||||
payload: newThresholds,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ALERT_THRESHOLD_STATE,
|
||||
thresholds: newThresholds,
|
||||
});
|
||||
@@ -272,7 +272,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
thresholds: [],
|
||||
};
|
||||
const result = alertThresholdReducer(modifiedState, { type: 'RESET' });
|
||||
expect(result).toEqual(INITIAL_ALERT_THRESHOLD_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ALERT_THRESHOLD_STATE);
|
||||
});
|
||||
|
||||
it(TEST_SET_INITIAL_STATE_FROM_PAYLOAD, () => {
|
||||
@@ -289,7 +289,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_INITIAL_STATE',
|
||||
payload: newState,
|
||||
});
|
||||
expect(result).toEqual(newState);
|
||||
expect(result).toStrictEqual(newState);
|
||||
});
|
||||
|
||||
it(TEST_RETURN_STATE_FOR_UNKNOWN_ACTION, () => {
|
||||
@@ -298,7 +298,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
|
||||
{ type: UNKNOWN_ACTION_TYPE } as any,
|
||||
);
|
||||
expect(result).toEqual(INITIAL_ALERT_THRESHOLD_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ALERT_THRESHOLD_STATE);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -308,7 +308,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_SEND_NOTIFICATION_IF_DATA_IS_MISSING',
|
||||
payload: { toleranceLimit: 21, timeUnit: UniversalYAxisUnit.HOURS },
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
sendNotificationIfDataIsMissing: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.sendNotificationIfDataIsMissing,
|
||||
@@ -323,7 +323,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'TOGGLE_SEND_NOTIFICATION_IF_DATA_IS_MISSING',
|
||||
payload: true,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
sendNotificationIfDataIsMissing: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.sendNotificationIfDataIsMissing,
|
||||
@@ -337,7 +337,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_ENFORCE_MINIMUM_DATAPOINTS',
|
||||
payload: { minimumDatapoints: 10 },
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
enforceMinimumDatapoints: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.enforceMinimumDatapoints,
|
||||
@@ -351,7 +351,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'TOGGLE_ENFORCE_MINIMUM_DATAPOINTS',
|
||||
payload: true,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
enforceMinimumDatapoints: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.enforceMinimumDatapoints,
|
||||
@@ -365,7 +365,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_DELAY_EVALUATION',
|
||||
payload: { delay: 10, timeUnit: UniversalYAxisUnit.HOURS },
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
delayEvaluation: { delay: 10, timeUnit: UniversalYAxisUnit.HOURS },
|
||||
});
|
||||
@@ -386,7 +386,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_EVALUATION_CADENCE',
|
||||
payload: newCadence,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
evaluationCadence: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.evaluationCadence,
|
||||
@@ -400,7 +400,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_EVALUATION_CADENCE_MODE',
|
||||
payload: 'custom',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE,
|
||||
evaluationCadence: {
|
||||
...INITIAL_ADVANCED_OPTIONS_STATE.evaluationCadence,
|
||||
@@ -415,7 +415,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
delayEvaluation: { delay: 10, timeUnit: UniversalYAxisUnit.HOURS },
|
||||
};
|
||||
const result = advancedOptionsReducer(modifiedState, { type: 'RESET' });
|
||||
expect(result).toEqual(INITIAL_ADVANCED_OPTIONS_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ADVANCED_OPTIONS_STATE);
|
||||
});
|
||||
|
||||
it(TEST_SET_INITIAL_STATE_FROM_PAYLOAD, () => {
|
||||
@@ -431,7 +431,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_INITIAL_STATE',
|
||||
payload: newState,
|
||||
});
|
||||
expect(result).toEqual(newState);
|
||||
expect(result).toStrictEqual(newState);
|
||||
});
|
||||
|
||||
it(TEST_RETURN_STATE_FOR_UNKNOWN_ACTION, () => {
|
||||
@@ -440,7 +440,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
|
||||
{ type: UNKNOWN_ACTION_TYPE } as any,
|
||||
);
|
||||
expect(result).toEqual(INITIAL_ADVANCED_OPTIONS_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_ADVANCED_OPTIONS_STATE);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -455,7 +455,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_WINDOW_TYPE',
|
||||
payload: 'rolling',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
windowType: 'rolling',
|
||||
timeframe: INITIAL_EVALUATION_WINDOW_STATE.timeframe,
|
||||
startingAt: INITIAL_EVALUATION_WINDOW_STATE.startingAt,
|
||||
@@ -467,7 +467,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_WINDOW_TYPE',
|
||||
payload: 'cumulative',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
windowType: 'cumulative',
|
||||
timeframe: 'currentHour',
|
||||
startingAt: INITIAL_EVALUATION_WINDOW_STATE.startingAt,
|
||||
@@ -479,7 +479,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_TIMEFRAME',
|
||||
payload: '10m0s',
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_EVALUATION_WINDOW_STATE,
|
||||
timeframe: '10m0s',
|
||||
});
|
||||
@@ -496,7 +496,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_STARTING_AT',
|
||||
payload: newStartingAt,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_EVALUATION_WINDOW_STATE,
|
||||
startingAt: newStartingAt,
|
||||
});
|
||||
@@ -514,7 +514,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
},
|
||||
};
|
||||
const result = evaluationWindowReducer(modifiedState, { type: 'RESET' });
|
||||
expect(result).toEqual(INITIAL_EVALUATION_WINDOW_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_EVALUATION_WINDOW_STATE);
|
||||
});
|
||||
|
||||
it(TEST_SET_INITIAL_STATE_FROM_PAYLOAD, () => {
|
||||
@@ -532,7 +532,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_INITIAL_STATE',
|
||||
payload: newState,
|
||||
});
|
||||
expect(result).toEqual(newState);
|
||||
expect(result).toStrictEqual(newState);
|
||||
});
|
||||
|
||||
it(TEST_RETURN_STATE_FOR_UNKNOWN_ACTION, () => {
|
||||
@@ -541,7 +541,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
|
||||
{ type: UNKNOWN_ACTION_TYPE } as any,
|
||||
);
|
||||
expect(result).toEqual(INITIAL_EVALUATION_WINDOW_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_EVALUATION_WINDOW_STATE);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -555,7 +555,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
payload: notifications,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_NOTIFICATION_SETTINGS_STATE,
|
||||
multipleNotifications: notifications,
|
||||
});
|
||||
@@ -570,7 +570,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
type: 'SET_MULTIPLE_NOTIFICATIONS',
|
||||
payload: null,
|
||||
});
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...modifiedState,
|
||||
multipleNotifications: null,
|
||||
});
|
||||
@@ -590,7 +590,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
payload: reNotification,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_NOTIFICATION_SETTINGS_STATE,
|
||||
reNotification,
|
||||
});
|
||||
@@ -605,7 +605,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
payload: description,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_NOTIFICATION_SETTINGS_STATE,
|
||||
description,
|
||||
});
|
||||
@@ -619,7 +619,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
payload: true,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
...INITIAL_NOTIFICATION_SETTINGS_STATE,
|
||||
routingPolicies: true,
|
||||
});
|
||||
@@ -640,7 +640,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
const result = notificationSettingsReducer(modifiedState, {
|
||||
type: 'RESET',
|
||||
});
|
||||
expect(result).toEqual(INITIAL_NOTIFICATION_SETTINGS_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_NOTIFICATION_SETTINGS_STATE);
|
||||
});
|
||||
|
||||
it(TEST_SET_INITIAL_STATE_FROM_PAYLOAD, () => {
|
||||
@@ -662,7 +662,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
payload: newState,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual(newState);
|
||||
expect(result).toStrictEqual(newState);
|
||||
});
|
||||
|
||||
it(TEST_RETURN_STATE_FOR_UNKNOWN_ACTION, () => {
|
||||
@@ -671,7 +671,7 @@ describe('CreateAlertV2 Context Utils', () => {
|
||||
|
||||
{ type: UNKNOWN_ACTION_TYPE } as any,
|
||||
);
|
||||
expect(result).toEqual(INITIAL_NOTIFICATION_SETTINGS_STATE);
|
||||
expect(result).toStrictEqual(INITIAL_NOTIFICATION_SETTINGS_STATE);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -113,7 +113,7 @@ describe('CustomDomainSettings', () => {
|
||||
await user.click(screen.getByRole('button', { name: /apply changes/i }));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(capturedBody).toEqual({ name: 'myteam' });
|
||||
expect(capturedBody).toStrictEqual({ name: 'myteam' });
|
||||
});
|
||||
});
|
||||
|
||||
@@ -143,9 +143,9 @@ describe('CustomDomainSettings', () => {
|
||||
await user.type(input, 'myteam');
|
||||
await user.click(screen.getByRole('button', { name: /apply changes/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByRole('button', { name: /contact support/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('button', { name: /contact support/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('shows validation error when subdomain is less than 3 characters', async () => {
|
||||
@@ -255,7 +255,7 @@ describe('CustomDomainSettings', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(await screen.findByText('My Org Name')).toBeInTheDocument();
|
||||
await expect(screen.findByText('My Org Name')).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('falls back to customDomainSubdomain when org displayName is missing', async () => {
|
||||
@@ -269,7 +269,7 @@ describe('CustomDomainSettings', () => {
|
||||
appContextOverrides: { org: [] },
|
||||
});
|
||||
|
||||
expect(await screen.findByText('custom-host')).toBeInTheDocument();
|
||||
await expect(screen.findByText('custom-host')).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('falls back to activeHost.name when neither org name nor custom domain exists', async () => {
|
||||
@@ -294,7 +294,9 @@ describe('CustomDomainSettings', () => {
|
||||
});
|
||||
|
||||
// 'accepted-starfish' is the default host's name
|
||||
expect(await screen.findByText('accepted-starfish')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('accepted-starfish'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('does not render the card name row if workspaceName is totally falsy', async () => {
|
||||
|
||||
@@ -155,7 +155,7 @@ describe('VariableItem Component', () => {
|
||||
jest.clearAllMocks();
|
||||
});
|
||||
|
||||
test('renders without crashing', () => {
|
||||
it('renders without crashing', () => {
|
||||
renderVariableItem();
|
||||
|
||||
expect(screen.getByText(TEXT.ALL_VARIABLES)).toBeInTheDocument();
|
||||
@@ -165,7 +165,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('Variable Name Validation', () => {
|
||||
test('shows error when variable name already exists', () => {
|
||||
it('shows error when variable name already exists', () => {
|
||||
// Set validateName to return false (name exists)
|
||||
const mockValidateName = jest.fn().mockReturnValue(false);
|
||||
|
||||
@@ -181,7 +181,7 @@ describe('VariableItem Component', () => {
|
||||
// We won't check for button disabled state as it might be inconsistent in tests
|
||||
});
|
||||
|
||||
test('allows save when current variable name is used', () => {
|
||||
it('allows save when current variable name is used', () => {
|
||||
// Mock validate to return false for all other names but true for own name
|
||||
const mockValidateName = jest
|
||||
.fn()
|
||||
@@ -197,7 +197,7 @@ describe('VariableItem Component', () => {
|
||||
expect(screen.queryByText(TEXT.VARIABLE_EXISTS)).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('shows error when variable name contains whitespace', () => {
|
||||
it('shows error when variable name contains whitespace', () => {
|
||||
renderVariableItem({ ...basicVariableData, name: '' });
|
||||
|
||||
// Enter a name with whitespace
|
||||
@@ -212,7 +212,7 @@ describe('VariableItem Component', () => {
|
||||
expect(saveButton).toBeDisabled();
|
||||
});
|
||||
|
||||
test('allows variable name without whitespace', () => {
|
||||
it('allows variable name without whitespace', () => {
|
||||
renderVariableItem({ ...basicVariableData, name: '' });
|
||||
|
||||
// Enter a valid name without whitespace
|
||||
@@ -223,7 +223,7 @@ describe('VariableItem Component', () => {
|
||||
expect(screen.queryByText(TEXT.VARIABLE_WHITESPACE)).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('validates whitespace in auto-generated name for dynamic variables', () => {
|
||||
it('validates whitespace in auto-generated name for dynamic variables', () => {
|
||||
// Create a dynamic variable with empty name
|
||||
const dynamicVariable: IDashboardVariable = {
|
||||
...basicVariableData,
|
||||
@@ -241,7 +241,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('Dynamic Variable Attribute Key Validation', () => {
|
||||
test('shows error when attribute key already exists', async () => {
|
||||
it('shows error when attribute key already exists', async () => {
|
||||
// Mock validateAttributeKey to return false (attribute key exists)
|
||||
const mockValidateAttributeKey = jest.fn().mockReturnValue(false);
|
||||
|
||||
@@ -277,7 +277,7 @@ describe('VariableItem Component', () => {
|
||||
expect(saveButton).toBeDisabled();
|
||||
});
|
||||
|
||||
test('allows saving when attribute key is unique', async () => {
|
||||
it('allows saving when attribute key is unique', async () => {
|
||||
// Mock validateAttributeKey to return true (attribute key is unique)
|
||||
const mockValidateAttributeKey = jest.fn().mockReturnValue(true);
|
||||
|
||||
@@ -315,7 +315,7 @@ describe('VariableItem Component', () => {
|
||||
expect(saveButton).not.toBeDisabled();
|
||||
});
|
||||
|
||||
test('allows same attribute key for current variable being edited', async () => {
|
||||
it('allows same attribute key for current variable being edited', async () => {
|
||||
// Mock validateAttributeKey to return true for same variable
|
||||
const mockValidateAttributeKey = jest.fn().mockImplementation(
|
||||
(attributeKey, currentVariableId) =>
|
||||
@@ -348,7 +348,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('does not validate attribute key for non-dynamic variables', async () => {
|
||||
it('does not validate attribute key for non-dynamic variables', async () => {
|
||||
// Mock validateAttributeKey to return false (would show error for dynamic)
|
||||
const mockValidateAttributeKey = jest.fn().mockReturnValue(false);
|
||||
|
||||
@@ -377,7 +377,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('Variable Type Switching', () => {
|
||||
test('switches to CUSTOM variable type correctly', () => {
|
||||
it('switches to CUSTOM variable type correctly', () => {
|
||||
renderVariableItem();
|
||||
|
||||
// Find the Query button
|
||||
@@ -401,7 +401,7 @@ describe('VariableItem Component', () => {
|
||||
expect(screen.getByText(TEXT.OPTIONS)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('switches to TEXTBOX variable type correctly', () => {
|
||||
it('switches to TEXTBOX variable type correctly', () => {
|
||||
renderVariableItem();
|
||||
|
||||
// Find and click Textbox button
|
||||
@@ -424,7 +424,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('MultiSelect and ALL Option', () => {
|
||||
test('enables ALL option only when multiSelect is enabled', async () => {
|
||||
it('enables ALL option only when multiSelect is enabled', async () => {
|
||||
renderVariableItem();
|
||||
|
||||
// Initially, ALL option should not be visible
|
||||
@@ -457,7 +457,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('disables ALL option when multiSelect is disabled', async () => {
|
||||
it('disables ALL option when multiSelect is disabled', async () => {
|
||||
// Create variable with multiSelect and showALLOption both enabled
|
||||
const variable: IDashboardVariable = {
|
||||
...basicVariableData,
|
||||
@@ -501,7 +501,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('Cancel and Navigation', () => {
|
||||
test('calls onCancel when clicking All Variables button', () => {
|
||||
it('calls onCancel when clicking All Variables button', () => {
|
||||
renderVariableItem();
|
||||
|
||||
// Click All variables button
|
||||
@@ -511,7 +511,7 @@ describe('VariableItem Component', () => {
|
||||
expect(onCancel).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
test('calls onCancel when clicking Discard button', () => {
|
||||
it('calls onCancel when clicking Discard button', () => {
|
||||
renderVariableItem();
|
||||
|
||||
// Click Discard button
|
||||
@@ -550,7 +550,7 @@ describe('VariableItem Component', () => {
|
||||
};
|
||||
|
||||
// Test for cyclic dependency detection
|
||||
test('detects circular dependency and shows error message', async () => {
|
||||
it('detects circular dependency and shows error message', async () => {
|
||||
// Create variables with circular dependency
|
||||
const variable1 = createVariable(
|
||||
TEST_VAR_IDS.VAR1,
|
||||
@@ -577,7 +577,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
// Test for saving with no circular dependency
|
||||
test('allows saving when no circular dependency exists', async () => {
|
||||
it('allows saving when no circular dependency exists', async () => {
|
||||
// Create variables without circular dependency
|
||||
const variable1 = createVariable(
|
||||
TEST_VAR_IDS.VAR1,
|
||||
@@ -608,7 +608,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
// Test with multiple variable formats in query
|
||||
test('detects circular dependency with different variable formats', async () => {
|
||||
it('detects circular dependency with different variable formats', async () => {
|
||||
// Create variables with circular dependency using different formats
|
||||
const variable1 = createVariable(
|
||||
TEST_VAR_IDS.VAR1,
|
||||
@@ -645,7 +645,7 @@ describe('VariableItem Component', () => {
|
||||
});
|
||||
|
||||
describe('Textbox Variable Default Value Handling', () => {
|
||||
test('saves textbox variable with defaultValue and selectedValue set to textboxValue', async () => {
|
||||
it('saves textbox variable with defaultValue and selectedValue set to textboxValue', async () => {
|
||||
const user = userEvent.setup();
|
||||
const textboxVariable: IDashboardVariable = {
|
||||
id: TEST_VAR_IDS.VAR1,
|
||||
@@ -676,7 +676,7 @@ describe('VariableItem Component', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('saves textbox variable with empty values when textboxValue is empty', async () => {
|
||||
it('saves textbox variable with empty values when textboxValue is empty', async () => {
|
||||
const user = userEvent.setup();
|
||||
const textboxVariable: IDashboardVariable = {
|
||||
id: TEST_VAR_IDS.VAR1,
|
||||
@@ -707,7 +707,7 @@ describe('VariableItem Component', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('updates textbox defaultValue and selectedValue when user changes textboxValue input', async () => {
|
||||
it('updates textbox defaultValue and selectedValue when user changes textboxValue input', async () => {
|
||||
const user = userEvent.setup();
|
||||
const textboxVariable: IDashboardVariable = {
|
||||
id: TEST_VAR_IDS.VAR1,
|
||||
@@ -745,7 +745,7 @@ describe('VariableItem Component', () => {
|
||||
);
|
||||
});
|
||||
|
||||
test('non-textbox variables use variableDefaultValue instead of textboxValue', async () => {
|
||||
it('non-textbox variables use variableDefaultValue instead of textboxValue', async () => {
|
||||
const user = userEvent.setup();
|
||||
const queryVariable: IDashboardVariable = {
|
||||
id: TEST_VAR_IDS.VAR1,
|
||||
@@ -780,7 +780,7 @@ describe('VariableItem Component', () => {
|
||||
expect(savedVariable.defaultValue).not.toBe('should-not-be-used');
|
||||
});
|
||||
|
||||
test('switching to textbox type sets defaultValue and selectedValue correctly on save', async () => {
|
||||
it('switching to textbox type sets defaultValue and selectedValue correctly on save', async () => {
|
||||
const user = userEvent.setup();
|
||||
// Start with a QUERY variable
|
||||
const queryVariable: IDashboardVariable = {
|
||||
|
||||
@@ -38,7 +38,7 @@ function TableRow({ children, ...props }: RowProps): JSX.Element {
|
||||
transition,
|
||||
isDragging,
|
||||
} = useSortable({
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
id: props['data-row-key'],
|
||||
});
|
||||
|
||||
@@ -148,7 +148,7 @@ function VariablesSettings({
|
||||
});
|
||||
|
||||
if (name) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
variableNamesMap[name] = name;
|
||||
}
|
||||
|
||||
@@ -391,7 +391,7 @@ function VariablesSettings({
|
||||
const variableName = updatedVariables[index].name;
|
||||
|
||||
if (variableName) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
reArrangedVariables[variableName] = {
|
||||
...updatedVariables[index],
|
||||
order: index,
|
||||
|
||||
@@ -109,11 +109,13 @@ describe('PublicDashboardSetting', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(
|
||||
await screen.findByRole('checkbox', { name: /enable time range/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('checkbox', { name: /enable time range/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
expect(await screen.findByText(/default time range/i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/default time range/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
expect(screen.getByText(/Last 30 minutes/i)).toBeInTheDocument();
|
||||
|
||||
@@ -123,9 +125,9 @@ describe('PublicDashboardSetting', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(
|
||||
await screen.findByRole('button', { name: /publish dashboard/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('button', { name: /publish dashboard/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -149,9 +151,9 @@ describe('PublicDashboardSetting', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(
|
||||
await screen.findByRole('checkbox', { name: /enable time range/i }),
|
||||
).toBeChecked();
|
||||
await expect(
|
||||
screen.findByRole('checkbox', { name: /enable time range/i }),
|
||||
).resolves.toBeChecked();
|
||||
|
||||
await waitFor(() => {
|
||||
expect(screen.getByText(/default time range/i)).toBeInTheDocument();
|
||||
@@ -163,13 +165,13 @@ describe('PublicDashboardSetting', () => {
|
||||
expect(screen.getByText(/Public Dashboard URL/i)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(
|
||||
await screen.findByRole('button', { name: /update published dashboard/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('button', { name: /update published dashboard/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
expect(
|
||||
await screen.findByRole('button', { name: /unpublish dashboard/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('button', { name: /unpublish dashboard/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -249,7 +251,7 @@ describe('PublicDashboardSetting', () => {
|
||||
rest.post(publicDashboardURL, async (req, res, ctx) => {
|
||||
const body = await req.json();
|
||||
createApiCalled = true;
|
||||
expect(body).toEqual({
|
||||
expect(body).toStrictEqual({
|
||||
timeRangeEnabled: true,
|
||||
defaultTimeRange: DEFAULT_TIME_RANGE,
|
||||
});
|
||||
@@ -318,7 +320,7 @@ describe('PublicDashboardSetting', () => {
|
||||
|
||||
await waitFor(() => {
|
||||
expect(updateApiCalled).toBe(true);
|
||||
expect(capturedRequestBody).toEqual({
|
||||
expect(capturedRequestBody).toStrictEqual({
|
||||
timeRangeEnabled: true,
|
||||
defaultTimeRange: DEFAULT_TIME_RANGE,
|
||||
});
|
||||
|
||||
@@ -40,7 +40,7 @@ describe('VariableItem', () => {
|
||||
useEffectSpy.mockRestore();
|
||||
});
|
||||
|
||||
test('renders component with default props', () => {
|
||||
it('renders component with default props', () => {
|
||||
render(
|
||||
<MockQueryClientProvider>
|
||||
<VariableItem
|
||||
@@ -54,7 +54,7 @@ describe('VariableItem', () => {
|
||||
expect(screen.getByText('$testVariable')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('renders Input when the variable type is TEXTBOX', () => {
|
||||
it('renders Input when the variable type is TEXTBOX', () => {
|
||||
render(
|
||||
<MockQueryClientProvider>
|
||||
<VariableItem
|
||||
@@ -69,7 +69,7 @@ describe('VariableItem', () => {
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('calls onValueUpdate when Input value changes and blurs', async () => {
|
||||
it('calls onValueUpdate when Input value changes and blurs', async () => {
|
||||
render(
|
||||
<MockQueryClientProvider>
|
||||
<VariableItem
|
||||
@@ -102,7 +102,7 @@ describe('VariableItem', () => {
|
||||
});
|
||||
});
|
||||
|
||||
test('renders a Select element when variable type is CUSTOM', () => {
|
||||
it('renders a Select element when variable type is CUSTOM', () => {
|
||||
render(
|
||||
<MockQueryClientProvider>
|
||||
<VariableItem
|
||||
@@ -117,7 +117,7 @@ describe('VariableItem', () => {
|
||||
expect(screen.getByTestId('variable-select')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('renders a Select element with all selected', async () => {
|
||||
it('renders a Select element with all selected', async () => {
|
||||
const customVariableData = {
|
||||
...mockCustomVariableData,
|
||||
allSelected: true,
|
||||
@@ -138,7 +138,7 @@ describe('VariableItem', () => {
|
||||
expect(screen.getByText('ALL')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('calls useEffect when the component mounts', () => {
|
||||
it('calls useEffect when the component mounts', () => {
|
||||
render(
|
||||
<MockQueryClientProvider>
|
||||
<VariableItem
|
||||
|
||||
@@ -272,7 +272,7 @@ describe('DashboardVariableSelection', () => {
|
||||
);
|
||||
});
|
||||
|
||||
expect(callOrder).toEqual([
|
||||
expect(callOrder).toStrictEqual([
|
||||
'updateDashboardVariablesStore',
|
||||
'enqueueDescendantsOfVariable',
|
||||
]);
|
||||
|
||||
@@ -32,7 +32,7 @@ describe('VariableItem Default Value Selection Behavior', () => {
|
||||
});
|
||||
|
||||
describe('Single Select Variables', () => {
|
||||
test('should keep previous selection value', async () => {
|
||||
it('should keep previous selection value', async () => {
|
||||
const variable: IDashboardVariable = {
|
||||
id: TEST_VARIABLE_ID,
|
||||
name: TEST_VARIABLE_NAME,
|
||||
@@ -51,10 +51,10 @@ describe('VariableItem Default Value Selection Behavior', () => {
|
||||
expect(screen.getByTestId(VARIABLE_SELECT_TESTID)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(await screen.findByText('option1')).toBeInTheDocument();
|
||||
await expect(screen.findByText('option1')).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('should auto-select first option when no previous and no default', async () => {
|
||||
it('should auto-select first option when no previous and no default', async () => {
|
||||
const variable: IDashboardVariable = {
|
||||
id: TEST_VARIABLE_ID,
|
||||
name: TEST_VARIABLE_NAME,
|
||||
@@ -74,12 +74,12 @@ describe('VariableItem Default Value Selection Behavior', () => {
|
||||
});
|
||||
|
||||
// With the new variable select strategy, the first option is auto-selected
|
||||
expect(await screen.findByText('option1')).toBeInTheDocument();
|
||||
await expect(screen.findByText('option1')).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
describe('Multi Select Variables with ALL enabled', () => {
|
||||
test('should show ALL when all options are selected', async () => {
|
||||
it('should show ALL when all options are selected', async () => {
|
||||
const variable: IDashboardVariable = {
|
||||
id: TEST_VARIABLE_ID,
|
||||
name: TEST_VARIABLE_NAME,
|
||||
@@ -99,12 +99,12 @@ describe('VariableItem Default Value Selection Behavior', () => {
|
||||
expect(screen.getByTestId(VARIABLE_SELECT_TESTID)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(await screen.findByText('ALL')).toBeInTheDocument();
|
||||
await expect(screen.findByText('ALL')).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
describe('Multi Select Variables with ALL disabled', () => {
|
||||
test('should show placeholder when no selection', async () => {
|
||||
it('should show placeholder when no selection', async () => {
|
||||
const variable: IDashboardVariable = {
|
||||
id: TEST_VARIABLE_ID,
|
||||
name: TEST_VARIABLE_NAME,
|
||||
@@ -123,7 +123,7 @@ describe('VariableItem Default Value Selection Behavior', () => {
|
||||
expect(screen.getByTestId(VARIABLE_SELECT_TESTID)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
expect(await screen.findByText('Select value')).toBeInTheDocument();
|
||||
await expect(screen.findByText('Select value')).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -47,7 +47,7 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
},
|
||||
];
|
||||
|
||||
test.each(testCases)(
|
||||
it.each(testCases)(
|
||||
'should update variable node when $scenario',
|
||||
({ nodeToUpdate, expected }) => {
|
||||
const updatedVariables: string[] = [];
|
||||
@@ -57,7 +57,7 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
|
||||
onUpdateVariableNode(nodeToUpdate, graph, topologicalOrder, callback);
|
||||
|
||||
expect(updatedVariables).toEqual(expected);
|
||||
expect(updatedVariables).toStrictEqual(expected);
|
||||
},
|
||||
);
|
||||
|
||||
@@ -66,7 +66,7 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
onUpdateVariableNode('http_status_code', graph, [], (node) =>
|
||||
updatedVariables.push(node),
|
||||
);
|
||||
expect(updatedVariables).toEqual([]);
|
||||
expect(updatedVariables).toStrictEqual([]);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -87,11 +87,11 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
environment: [],
|
||||
};
|
||||
|
||||
expect(buildParentDependencyGraph(graph)).toEqual(expected);
|
||||
expect(buildParentDependencyGraph(graph)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle empty graph', () => {
|
||||
expect(buildParentDependencyGraph({})).toEqual({});
|
||||
expect(buildParentDependencyGraph({})).toStrictEqual({});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -142,13 +142,13 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
},
|
||||
};
|
||||
|
||||
expect(buildDependencyGraph(graph)).toEqual(expected);
|
||||
expect(buildDependencyGraph(graph)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should return empty transitiveDescendants for an empty graph', () => {
|
||||
const result = buildDependencyGraph({});
|
||||
expect(result.transitiveDescendants).toEqual({});
|
||||
expect(result.order).toEqual([]);
|
||||
expect(result.transitiveDescendants).toStrictEqual({});
|
||||
expect(result.order).toStrictEqual([]);
|
||||
expect(result.hasCycle).toBe(false);
|
||||
});
|
||||
|
||||
@@ -159,7 +159,7 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
c: [],
|
||||
};
|
||||
const result = buildDependencyGraph(linearGraph);
|
||||
expect(result.transitiveDescendants).toEqual({
|
||||
expect(result.transitiveDescendants).toStrictEqual({
|
||||
a: ['b', 'c'],
|
||||
b: ['c'],
|
||||
c: [],
|
||||
@@ -174,13 +174,13 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
d: [],
|
||||
};
|
||||
const result = buildDependencyGraph(diamondGraph);
|
||||
expect(result.transitiveDescendants.a).toEqual(
|
||||
expect(result.transitiveDescendants.a).toStrictEqual(
|
||||
expect.arrayContaining(['b', 'c', 'd']),
|
||||
);
|
||||
expect(result.transitiveDescendants.a).toHaveLength(3);
|
||||
expect(result.transitiveDescendants.b).toEqual(['d']);
|
||||
expect(result.transitiveDescendants.c).toEqual(['d']);
|
||||
expect(result.transitiveDescendants.d).toEqual([]);
|
||||
expect(result.transitiveDescendants.b).toStrictEqual(['d']);
|
||||
expect(result.transitiveDescendants.c).toStrictEqual(['d']);
|
||||
expect(result.transitiveDescendants.d).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle disconnected components in transitiveDescendants', () => {
|
||||
@@ -191,10 +191,10 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
y: [],
|
||||
};
|
||||
const result = buildDependencyGraph(disconnectedGraph);
|
||||
expect(result.transitiveDescendants.a).toEqual(['b']);
|
||||
expect(result.transitiveDescendants.b).toEqual([]);
|
||||
expect(result.transitiveDescendants.x).toEqual(['y']);
|
||||
expect(result.transitiveDescendants.y).toEqual([]);
|
||||
expect(result.transitiveDescendants.a).toStrictEqual(['b']);
|
||||
expect(result.transitiveDescendants.b).toStrictEqual([]);
|
||||
expect(result.transitiveDescendants.x).toStrictEqual(['y']);
|
||||
expect(result.transitiveDescendants.y).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should return empty transitiveDescendants for all leaf nodes', () => {
|
||||
@@ -204,7 +204,7 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
c: [],
|
||||
};
|
||||
const result = buildDependencyGraph(leafOnlyGraph);
|
||||
expect(result.transitiveDescendants).toEqual({
|
||||
expect(result.transitiveDescendants).toStrictEqual({
|
||||
a: [],
|
||||
b: [],
|
||||
c: [],
|
||||
@@ -225,11 +225,11 @@ describe('dashboardVariables - utilities and processors', () => {
|
||||
environment: [],
|
||||
};
|
||||
|
||||
expect(buildDependencies(variables)).toEqual(expected);
|
||||
expect(buildDependencies(variables)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle empty variables array', () => {
|
||||
expect(buildDependencies([])).toEqual({});
|
||||
expect(buildDependencies([])).toStrictEqual({});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -36,7 +36,7 @@ export const convertVariablesToDbFormat = (
|
||||
variblesArr.reduce((result, obj: IDashboardVariable) => {
|
||||
const { id } = obj;
|
||||
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
result[id] = obj;
|
||||
return result;
|
||||
}, {});
|
||||
|
||||
@@ -81,7 +81,7 @@ describe('onUpdateVariableNode', () => {
|
||||
|
||||
onUpdateVariableNode('deployment', graph, topologicalOrder, callback);
|
||||
|
||||
expect(visited).toEqual(['deployment', 'namespace', 'service', 'pod']);
|
||||
expect(visited).toStrictEqual(['deployment', 'namespace', 'service', 'pod']);
|
||||
});
|
||||
|
||||
it('should call callback starting from a middle node', () => {
|
||||
@@ -92,7 +92,7 @@ describe('onUpdateVariableNode', () => {
|
||||
|
||||
onUpdateVariableNode('namespace', graph, topologicalOrder, callback);
|
||||
|
||||
expect(visited).toEqual(['namespace', 'service', 'pod']);
|
||||
expect(visited).toStrictEqual(['namespace', 'service', 'pod']);
|
||||
});
|
||||
|
||||
it('should only call callback for the leaf node when updating leaf', () => {
|
||||
@@ -103,7 +103,7 @@ describe('onUpdateVariableNode', () => {
|
||||
|
||||
onUpdateVariableNode('pod', graph, topologicalOrder, callback);
|
||||
|
||||
expect(visited).toEqual(['pod']);
|
||||
expect(visited).toStrictEqual(['pod']);
|
||||
});
|
||||
|
||||
it('should handle CUSTOM variable not in topologicalOrder by updating its children', () => {
|
||||
@@ -116,7 +116,7 @@ describe('onUpdateVariableNode', () => {
|
||||
onUpdateVariableNode('customVar', graph, topologicalOrder, callback);
|
||||
|
||||
// Should process namespace and its descendants (service, pod)
|
||||
expect(visited).toEqual(['namespace', 'service', 'pod']);
|
||||
expect(visited).toStrictEqual(['namespace', 'service', 'pod']);
|
||||
});
|
||||
|
||||
it('should handle node not in graph gracefully', () => {
|
||||
@@ -128,7 +128,7 @@ describe('onUpdateVariableNode', () => {
|
||||
onUpdateVariableNode('unknownNode', graph, topologicalOrder, callback);
|
||||
|
||||
// Should not call callback for any node since unknownNode has no children
|
||||
expect(visited).toEqual([]);
|
||||
expect(visited).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle empty graph', () => {
|
||||
@@ -140,7 +140,7 @@ describe('onUpdateVariableNode', () => {
|
||||
onUpdateVariableNode('deployment', {}, topologicalOrder, callback);
|
||||
|
||||
// deployment is in topologicalOrder, so callback is called for it
|
||||
expect(visited).toEqual(['deployment']);
|
||||
expect(visited).toStrictEqual(['deployment']);
|
||||
});
|
||||
|
||||
it('should handle empty topologicalOrder', () => {
|
||||
@@ -151,7 +151,7 @@ describe('onUpdateVariableNode', () => {
|
||||
|
||||
onUpdateVariableNode('deployment', graph, [], callback);
|
||||
|
||||
expect(visited).toEqual([]);
|
||||
expect(visited).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should handle CUSTOM variable with multiple children', () => {
|
||||
@@ -173,7 +173,7 @@ describe('onUpdateVariableNode', () => {
|
||||
);
|
||||
|
||||
// Should process namespace, service, and pod (descendants)
|
||||
expect(visited).toEqual(['namespace', 'service', 'pod']);
|
||||
expect(visited).toStrictEqual(['namespace', 'service', 'pod']);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -200,11 +200,15 @@ function makeDynamicVar(
|
||||
|
||||
describe('mergeUniqueStrings', () => {
|
||||
it('should merge two arrays and deduplicate', () => {
|
||||
expect(mergeUniqueStrings(['a', 'b'], ['b', 'c'])).toEqual(['a', 'b', 'c']);
|
||||
expect(mergeUniqueStrings(['a', 'b'], ['b', 'c'])).toStrictEqual([
|
||||
'a',
|
||||
'b',
|
||||
'c',
|
||||
]);
|
||||
});
|
||||
|
||||
it('should convert numbers and booleans to strings', () => {
|
||||
expect(mergeUniqueStrings([1, true, 'hello'], [2, false])).toEqual([
|
||||
expect(mergeUniqueStrings([1, true, 'hello'], [2, false])).toStrictEqual([
|
||||
'1',
|
||||
'true',
|
||||
'hello',
|
||||
@@ -214,15 +218,15 @@ describe('mergeUniqueStrings', () => {
|
||||
});
|
||||
|
||||
it('should deduplicate when number and its string form both appear', () => {
|
||||
expect(mergeUniqueStrings([42], ['42'])).toEqual(['42']);
|
||||
expect(mergeUniqueStrings([42], ['42'])).toStrictEqual(['42']);
|
||||
});
|
||||
|
||||
it('should handle a single array', () => {
|
||||
expect(mergeUniqueStrings(['x', 'y', 'x'])).toEqual(['x', 'y']);
|
||||
expect(mergeUniqueStrings(['x', 'y', 'x'])).toStrictEqual(['x', 'y']);
|
||||
});
|
||||
|
||||
it('should handle three or more arrays', () => {
|
||||
expect(mergeUniqueStrings(['a'], ['b'], ['c'], ['a', 'c'])).toEqual([
|
||||
expect(mergeUniqueStrings(['a'], ['b'], ['c'], ['a', 'c'])).toStrictEqual([
|
||||
'a',
|
||||
'b',
|
||||
'c',
|
||||
@@ -230,15 +234,19 @@ describe('mergeUniqueStrings', () => {
|
||||
});
|
||||
|
||||
it('should return empty array when no arrays are provided', () => {
|
||||
expect(mergeUniqueStrings()).toEqual([]);
|
||||
expect(mergeUniqueStrings()).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should return empty array when all input arrays are empty', () => {
|
||||
expect(mergeUniqueStrings([], [], [])).toEqual([]);
|
||||
expect(mergeUniqueStrings([], [], [])).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('should preserve order of first occurrence', () => {
|
||||
expect(mergeUniqueStrings(['c', 'a'], ['b', 'a'])).toEqual(['c', 'a', 'b']);
|
||||
expect(mergeUniqueStrings(['c', 'a'], ['b', 'a'])).toStrictEqual([
|
||||
'c',
|
||||
'a',
|
||||
'b',
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -424,7 +424,7 @@ describe('Panel Management Tests', () => {
|
||||
);
|
||||
|
||||
// Should return dashboard unchanged
|
||||
expect(updatedDashboard).toEqual(dashboard);
|
||||
expect(updatedDashboard).toStrictEqual(dashboard);
|
||||
});
|
||||
|
||||
it('should handle undefined dashboard gracefully', () => {
|
||||
|
||||
@@ -13,7 +13,7 @@ describe('stackUtils', () => {
|
||||
[4, 5, 6],
|
||||
];
|
||||
const { data: result } = stack(data, neverOmit);
|
||||
expect(result[0]).toEqual([100, 200, 300]);
|
||||
expect(result[0]).toStrictEqual([100, 200, 300]);
|
||||
});
|
||||
|
||||
it('stacks value series cumulatively (last = raw, first = total)', () => {
|
||||
@@ -26,9 +26,9 @@ describe('stackUtils', () => {
|
||||
];
|
||||
const { data: result } = stack(data, neverOmit);
|
||||
// result[1] = s1+s2+s3, result[2] = s2+s3, result[3] = s3
|
||||
expect(result[1]).toEqual([12, 15, 18]); // 1+4+7, 2+5+8, 3+6+9
|
||||
expect(result[2]).toEqual([11, 13, 15]); // 4+7, 5+8, 6+9
|
||||
expect(result[3]).toEqual([7, 8, 9]);
|
||||
expect(result[1]).toStrictEqual([12, 15, 18]); // 1+4+7, 2+5+8, 3+6+9
|
||||
expect(result[2]).toStrictEqual([11, 13, 15]); // 4+7, 5+8, 6+9
|
||||
expect(result[3]).toStrictEqual([7, 8, 9]);
|
||||
});
|
||||
|
||||
it('treats null values as 0 when stacking', () => {
|
||||
@@ -38,8 +38,8 @@ describe('stackUtils', () => {
|
||||
[null, 10],
|
||||
];
|
||||
const { data: result } = stack(data, neverOmit);
|
||||
expect(result[1]).toEqual([1, 10]); // total
|
||||
expect(result[2]).toEqual([0, 10]); // last series with null→0
|
||||
expect(result[1]).toStrictEqual([1, 10]); // total
|
||||
expect(result[2]).toStrictEqual([0, 10]); // last series with null→0
|
||||
});
|
||||
|
||||
it('copies omitted series as-is without accumulating', () => {
|
||||
@@ -53,9 +53,9 @@ describe('stackUtils', () => {
|
||||
const omitSeries2 = (i: number): boolean => i === 2;
|
||||
const { data: result } = stack(data, omitSeries2);
|
||||
// series 3 raw: [1, 2]; series 2 omitted: [100, 200] as-is; series 1 stacked with s3: [11, 22]
|
||||
expect(result[1]).toEqual([11, 22]); // 10+1, 20+2
|
||||
expect(result[2]).toEqual([100, 200]); // copied, not stacked
|
||||
expect(result[3]).toEqual([1, 2]);
|
||||
expect(result[1]).toStrictEqual([11, 22]); // 10+1, 20+2
|
||||
expect(result[2]).toStrictEqual([100, 200]); // copied, not stacked
|
||||
expect(result[3]).toStrictEqual([1, 2]);
|
||||
});
|
||||
|
||||
it('returns bands between consecutive visible series when none omitted', () => {
|
||||
@@ -66,7 +66,7 @@ describe('stackUtils', () => {
|
||||
[5, 6],
|
||||
];
|
||||
const { bands } = stack(data, neverOmit);
|
||||
expect(bands).toEqual([{ series: [1, 2] }, { series: [2, 3] }]);
|
||||
expect(bands).toStrictEqual([{ series: [1, 2] }, { series: [2, 3] }]);
|
||||
});
|
||||
|
||||
it('returns bands only between visible series when some are omitted', () => {
|
||||
@@ -74,7 +74,7 @@ describe('stackUtils', () => {
|
||||
const data: AlignedData = [[0], [1], [2], [3], [4]];
|
||||
const omitSeries2 = (i: number): boolean => i === 2;
|
||||
const { bands } = stack(data, omitSeries2);
|
||||
expect(bands).toEqual([{ series: [1, 3] }, { series: [3, 4] }]);
|
||||
expect(bands).toStrictEqual([{ series: [1, 3] }, { series: [3, 4] }]);
|
||||
});
|
||||
|
||||
it('returns empty bands when only one value series', () => {
|
||||
@@ -83,30 +83,30 @@ describe('stackUtils', () => {
|
||||
[1, 2],
|
||||
];
|
||||
const { bands } = stack(data, neverOmit);
|
||||
expect(bands).toEqual([]);
|
||||
expect(bands).toStrictEqual([]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('getInitialStackedBands', () => {
|
||||
it('returns one band between each consecutive pair for seriesCount 3', () => {
|
||||
expect(getInitialStackedBands(3)).toEqual([
|
||||
expect(getInitialStackedBands(3)).toStrictEqual([
|
||||
{ series: [1, 2] },
|
||||
{ series: [2, 3] },
|
||||
]);
|
||||
});
|
||||
|
||||
it('returns empty array for seriesCount 0 or 1', () => {
|
||||
expect(getInitialStackedBands(0)).toEqual([]);
|
||||
expect(getInitialStackedBands(1)).toEqual([]);
|
||||
expect(getInitialStackedBands(0)).toStrictEqual([]);
|
||||
expect(getInitialStackedBands(1)).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('returns single band for seriesCount 2', () => {
|
||||
expect(getInitialStackedBands(2)).toEqual([{ series: [1, 2] }]);
|
||||
expect(getInitialStackedBands(2)).toStrictEqual([{ series: [1, 2] }]);
|
||||
});
|
||||
|
||||
it('returns bands [1,2], [2,3], ..., [n-1, n] for seriesCount n', () => {
|
||||
const bands = getInitialStackedBands(5);
|
||||
expect(bands).toEqual([
|
||||
expect(bands).toStrictEqual([
|
||||
{ series: [1, 2] },
|
||||
{ series: [2, 3] },
|
||||
{ series: [3, 4] },
|
||||
|
||||
@@ -119,9 +119,9 @@ describe('useBarChartStacking', () => {
|
||||
}),
|
||||
);
|
||||
// Still returns stacked data (computed in useMemo); no hooks registered
|
||||
expect(result.current[0]).toEqual([0, 1]);
|
||||
expect(result.current[1]).toEqual([5, 7]); // stacked
|
||||
expect(result.current[2]).toEqual([4, 5]);
|
||||
expect(result.current[0]).toStrictEqual([0, 1]);
|
||||
expect(result.current[1]).toStrictEqual([5, 7]); // stacked
|
||||
expect(result.current[2]).toStrictEqual([4, 5]);
|
||||
});
|
||||
|
||||
it('returns stacked data when isStackedBarChart is true and multiple value series', () => {
|
||||
@@ -138,10 +138,10 @@ describe('useBarChartStacking', () => {
|
||||
config: null,
|
||||
}),
|
||||
);
|
||||
expect(result.current[0]).toEqual([0, 1, 2]);
|
||||
expect(result.current[1]).toEqual([12, 15, 18]); // s1+s2+s3
|
||||
expect(result.current[2]).toEqual([11, 13, 15]); // s2+s3
|
||||
expect(result.current[3]).toEqual([7, 8, 9]);
|
||||
expect(result.current[0]).toStrictEqual([0, 1, 2]);
|
||||
expect(result.current[1]).toStrictEqual([12, 15, 18]); // s1+s2+s3
|
||||
expect(result.current[2]).toStrictEqual([11, 13, 15]); // s2+s3
|
||||
expect(result.current[3]).toStrictEqual([7, 8, 9]);
|
||||
});
|
||||
|
||||
it('returns data as-is when only one value series (no stacking needed)', () => {
|
||||
@@ -156,7 +156,7 @@ describe('useBarChartStacking', () => {
|
||||
config: null,
|
||||
}),
|
||||
);
|
||||
expect(result.current).toEqual(data);
|
||||
expect(result.current).toStrictEqual(data);
|
||||
});
|
||||
|
||||
it('registers setData and setSeries hooks when isStackedBarChart and config provided', () => {
|
||||
|
||||
@@ -83,7 +83,7 @@ describe('TimeSeriesPanel utils', () => {
|
||||
const data = prepareChartData(apiResponse);
|
||||
|
||||
expect(data).toHaveLength(1);
|
||||
expect(data[0]).toEqual([]);
|
||||
expect(data[0]).toStrictEqual([]);
|
||||
});
|
||||
|
||||
it('returns timestamps and one series of y values for single series', () => {
|
||||
@@ -102,8 +102,8 @@ describe('TimeSeriesPanel utils', () => {
|
||||
const data = prepareChartData(apiResponse);
|
||||
|
||||
expect(data).toHaveLength(2);
|
||||
expect(data[0]).toEqual([1000, 2000]);
|
||||
expect(data[1]).toEqual([10, 20]);
|
||||
expect(data[0]).toStrictEqual([1000, 2000]);
|
||||
expect(data[1]).toStrictEqual([10, 20]);
|
||||
});
|
||||
|
||||
it('merges timestamps and fills missing values with null for multiple series', () => {
|
||||
@@ -128,11 +128,11 @@ describe('TimeSeriesPanel utils', () => {
|
||||
|
||||
const data = prepareChartData(apiResponse);
|
||||
|
||||
expect(data[0]).toEqual([1000, 2000, 3000]);
|
||||
expect(data[0]).toStrictEqual([1000, 2000, 3000]);
|
||||
// First series: 1, null, 3
|
||||
expect(data[1]).toEqual([1, null, 3]);
|
||||
expect(data[1]).toStrictEqual([1, null, 3]);
|
||||
// Second series: 10, 20, null
|
||||
expect(data[2]).toEqual([10, 20, null]);
|
||||
expect(data[2]).toStrictEqual([10, 20, null]);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -62,7 +62,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const result = getStoredSeriesVisibility('widget-1');
|
||||
|
||||
expect(result).not.toBeNull();
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{ label: 'CPU', show: true },
|
||||
{ label: 'Memory', show: false },
|
||||
]);
|
||||
@@ -85,7 +85,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const result = getStoredSeriesVisibility('widget-1');
|
||||
|
||||
expect(result).not.toBeNull();
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{ label: 'CPU', show: true },
|
||||
{ label: 'CPU', show: false },
|
||||
{ label: 'Memory', show: false },
|
||||
@@ -128,7 +128,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const stored = getStoredSeriesVisibility('widget-1');
|
||||
|
||||
expect(stored).not.toBeNull();
|
||||
expect(stored).toEqual([
|
||||
expect(stored).toStrictEqual([
|
||||
{ label: 'CPU', show: true },
|
||||
{ label: 'Memory', show: false },
|
||||
]);
|
||||
@@ -150,7 +150,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const stored = getStoredSeriesVisibility('widget-new');
|
||||
|
||||
expect(stored).not.toBeNull();
|
||||
expect(stored).toEqual([{ label: 'CPU', show: false }]);
|
||||
expect(stored).toStrictEqual([{ label: 'CPU', show: false }]);
|
||||
});
|
||||
|
||||
it('updates existing widget visibility when entry already exists', () => {
|
||||
@@ -176,7 +176,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const stored = getStoredSeriesVisibility('widget-1');
|
||||
|
||||
expect(stored).not.toBeNull();
|
||||
expect(stored).toEqual([
|
||||
expect(stored).toStrictEqual([
|
||||
{ label: 'CPU', show: false },
|
||||
{ label: 'Memory', show: true },
|
||||
]);
|
||||
@@ -202,7 +202,7 @@ describe('legendVisibilityUtils', () => {
|
||||
|
||||
const stored = getStoredSeriesVisibility('widget-1');
|
||||
expect(stored).not.toBeNull();
|
||||
expect(stored).toEqual([
|
||||
expect(stored).toStrictEqual([
|
||||
{ label: 'x-axis', show: true },
|
||||
{ label: 'CPU', show: false },
|
||||
]);
|
||||
@@ -232,10 +232,10 @@ describe('legendVisibilityUtils', () => {
|
||||
{ label: 'B', show: true },
|
||||
]);
|
||||
|
||||
expect(getStoredSeriesVisibility('widget-a')).toEqual([
|
||||
expect(getStoredSeriesVisibility('widget-a')).toStrictEqual([
|
||||
{ label: 'A', show: true },
|
||||
]);
|
||||
expect(getStoredSeriesVisibility('widget-b')).toEqual([
|
||||
expect(getStoredSeriesVisibility('widget-b')).toStrictEqual([
|
||||
{ label: 'B', show: true },
|
||||
]);
|
||||
});
|
||||
@@ -252,7 +252,7 @@ describe('legendVisibilityUtils', () => {
|
||||
);
|
||||
const [_, value] = (localStorage.setItem as jest.Mock).mock.calls[0];
|
||||
expect((): void => JSON.parse(value)).not.toThrow();
|
||||
expect(JSON.parse(value)).toEqual([
|
||||
expect(JSON.parse(value)).toStrictEqual([
|
||||
{ name: 'widget-1', dataIndex: [{ label: 'CPU', show: true }] },
|
||||
]);
|
||||
});
|
||||
@@ -263,7 +263,7 @@ describe('legendVisibilityUtils', () => {
|
||||
const raw = localStorage.getItem(storageKey);
|
||||
expect(raw).not.toBeNull();
|
||||
const parsed = JSON.parse(raw ?? '[]');
|
||||
expect(parsed).toEqual([{ name: 'widget-1', dataIndex: [] }]);
|
||||
expect(parsed).toStrictEqual([{ name: 'widget-1', dataIndex: [] }]);
|
||||
expect(getStoredSeriesVisibility('widget-1')).toBeNull();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -188,7 +188,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(await screen.findByText(/check your email/i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/check your email/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
expect(
|
||||
screen.getByText(/we've sent a password reset link/i),
|
||||
).toBeInTheDocument();
|
||||
@@ -208,7 +210,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(await screen.findByTestId('back-to-login')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByTestId('back-to-login'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('redirects to login when clicking back to login on success screen', async () => {
|
||||
@@ -225,7 +229,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(await screen.findByTestId('back-to-login')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByTestId('back-to-login'),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const backToLoginButton = screen.getByTestId('back-to-login');
|
||||
await user.click(backToLoginButton);
|
||||
@@ -250,7 +256,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(await screen.findByText(/user not found/i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/user not found/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('displays error message when API returns server error', async () => {
|
||||
@@ -263,9 +271,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(
|
||||
await screen.findByText(/internal server error occurred/i),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/internal server error occurred/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('clears error message on new submission attempt', async () => {
|
||||
@@ -295,7 +303,9 @@ describe('ForgotPassword Component', () => {
|
||||
const submitButton = screen.getByTestId('forgot-password-submit');
|
||||
await user.click(submitButton);
|
||||
|
||||
expect(await screen.findByText(/user not found/i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/user not found/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
// Click submit again
|
||||
await user.click(submitButton);
|
||||
@@ -303,7 +313,9 @@ describe('ForgotPassword Component', () => {
|
||||
await waitFor(() => {
|
||||
expect(screen.queryByText(/user not found/i)).not.toBeInTheDocument();
|
||||
});
|
||||
expect(await screen.findByText(/check your email/i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/check your email/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -336,7 +348,9 @@ describe('ForgotPassword Component', () => {
|
||||
await user.click(submitButton);
|
||||
|
||||
// Button should show loading state
|
||||
expect(await screen.findByText(/sending\.\.\./i)).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/sending\.\.\./i),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('disables submit button during loading', async () => {
|
||||
|
||||
@@ -76,7 +76,7 @@ describe('usePrefillAlertConditions', () => {
|
||||
builder: { queryData: [{ reduceTo: 'p90' }] },
|
||||
} as any),
|
||||
);
|
||||
expect(result.current.matchType).toBe(null);
|
||||
expect(result.current.matchType).toBeNull();
|
||||
});
|
||||
|
||||
it('returns the correct matchType for multiple queries with same time aggregation', () => {
|
||||
@@ -112,7 +112,7 @@ describe('usePrefillAlertConditions', () => {
|
||||
},
|
||||
} as any),
|
||||
);
|
||||
expect(result.current.matchType).toBe(null);
|
||||
expect(result.current.matchType).toBeNull();
|
||||
});
|
||||
|
||||
it('returns the correct op, target, targetUnit from the higher priority threshold for multiple thresholds', () => {
|
||||
|
||||
@@ -5,10 +5,10 @@ import { getUpdatedStepInterval } from './utils';
|
||||
describe('getUpdatedStepInterval', () => {
|
||||
it('should return 60', () => {
|
||||
const result = getUpdatedStepInterval('5m0s');
|
||||
expect(result).toEqual(60);
|
||||
expect(result).toBe(60);
|
||||
});
|
||||
it('should return 60 for 10m0s', () => {
|
||||
const result = getUpdatedStepInterval('10m0s');
|
||||
expect(result).toEqual(60);
|
||||
expect(result).toBe(60);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -44,7 +44,7 @@ describe('Table Panel utils', () => {
|
||||
expect(getQueryLegend(query, 'A')).toBe('p99');
|
||||
|
||||
// should return undefined when legend not present
|
||||
expect(getQueryLegend(query, 'B')).toBe(undefined);
|
||||
expect(getQueryLegend(query, 'B')).toBeUndefined();
|
||||
});
|
||||
|
||||
it('sorter function for table sorting', () => {
|
||||
|
||||
@@ -108,7 +108,7 @@ describe('EntityLogs', () => {
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
expect(capturedQueryRangePayloads.length).toBe(1);
|
||||
expect(capturedQueryRangePayloads).toHaveLength(1);
|
||||
});
|
||||
|
||||
await waitFor(async () => {
|
||||
@@ -131,7 +131,7 @@ describe('EntityLogs', () => {
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
expect(capturedQueryRangePayloads.length).toBe(2);
|
||||
expect(capturedQueryRangePayloads).toHaveLength(2);
|
||||
});
|
||||
|
||||
const firstPayload = capturedQueryRangePayloads[0];
|
||||
|
||||
@@ -149,7 +149,7 @@ describe('ServiceDetails for S3 Sync service', () => {
|
||||
expect(capturedPayload).not.toBeNull();
|
||||
});
|
||||
|
||||
expect(capturedPayload).toEqual({
|
||||
expect(capturedPayload).toStrictEqual({
|
||||
config: {
|
||||
aws: {
|
||||
logs: {
|
||||
|
||||
@@ -68,12 +68,12 @@ describe('filterAlerts', () => {
|
||||
|
||||
it('should return all alerts when filter is empty', () => {
|
||||
const result = filterAlerts(mockAlerts, '');
|
||||
expect(result).toEqual(mockAlerts);
|
||||
expect(result).toStrictEqual(mockAlerts);
|
||||
});
|
||||
|
||||
it('should return all alerts when filter is only whitespace', () => {
|
||||
const result = filterAlerts(mockAlerts, ' ');
|
||||
expect(result).toEqual(mockAlerts);
|
||||
expect(result).toStrictEqual(mockAlerts);
|
||||
});
|
||||
|
||||
it('should filter alerts by alert name', () => {
|
||||
|
||||
@@ -251,20 +251,20 @@ describe('ContextLogRenderer', () => {
|
||||
const afterQuery = (afterPayload.compositeQuery as any).queries[0].spec;
|
||||
|
||||
// Verify timestamps remain constant
|
||||
expect(afterStart).toEqual(initialPayload.start);
|
||||
expect(afterEnd).toEqual(initialPayload.end);
|
||||
expect(afterStart).toStrictEqual(initialPayload.start);
|
||||
expect(afterEnd).toStrictEqual(initialPayload.end);
|
||||
|
||||
// Verify offset changes
|
||||
expect(initialQuery.offset).toEqual(0);
|
||||
expect(afterQuery.offset).toEqual(10);
|
||||
expect(initialQuery.offset).toBe(0);
|
||||
expect(afterQuery.offset).toBe(10);
|
||||
|
||||
// Verify filter changes
|
||||
expect(initialQuery.filter.expression).toContain(expectedOpChange.before);
|
||||
expect(afterQuery.filter.expression).toContain(expectedOpChange.after);
|
||||
|
||||
// Verify query structure remains consistent
|
||||
expect(initialQuery.name).toEqual(afterQuery.name);
|
||||
expect(initialQuery.signal).toEqual(afterQuery.signal);
|
||||
expect(initialQuery.name).toStrictEqual(afterQuery.name);
|
||||
expect(initialQuery.signal).toStrictEqual(afterQuery.signal);
|
||||
};
|
||||
|
||||
it('should keep the start and end timestamps constant on clicking load more (prev / next) pages', async () => {
|
||||
|
||||
@@ -10,20 +10,20 @@ import {
|
||||
describe('recursiveParseJSON', () => {
|
||||
it('should return an empty object if the input is not valid JSON', () => {
|
||||
const result = recursiveParseJSON('not valid JSON');
|
||||
expect(result).toEqual({});
|
||||
expect(result).toStrictEqual({});
|
||||
});
|
||||
|
||||
it('should return the parsed JSON object for valid JSON input', () => {
|
||||
const jsonString = '{"name": "John", "age": 30}';
|
||||
const result = recursiveParseJSON(jsonString);
|
||||
expect(result).toEqual({ name: 'John', age: 30 });
|
||||
expect(result).toStrictEqual({ name: 'John', age: 30 });
|
||||
});
|
||||
|
||||
it('should recursively parse nested JSON objects', () => {
|
||||
const jsonString =
|
||||
'{"name": "John", "age": 30, "address": {"street": "123 Main St", "city": "Anytown", "state": "CA"}}';
|
||||
const result = recursiveParseJSON(jsonString);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
name: 'John',
|
||||
age: 30,
|
||||
address: {
|
||||
@@ -37,19 +37,21 @@ describe('recursiveParseJSON', () => {
|
||||
it('should recursively parse nested JSON arrays', () => {
|
||||
const jsonString = '[1, 2, [3, 4], {"foo": "bar"}]';
|
||||
const result = recursiveParseJSON(jsonString);
|
||||
expect(result).toEqual([1, 2, [3, 4], { foo: 'bar' }]);
|
||||
expect(result).toStrictEqual([1, 2, [3, 4], { foo: 'bar' }]);
|
||||
});
|
||||
|
||||
it('should recursively parse deeply nested JSON objects', () => {
|
||||
const jsonString = '{"foo": {"bar": {"baz": {"qux": {"value": 42}}}}}';
|
||||
const result = recursiveParseJSON(jsonString);
|
||||
expect(result).toEqual({ foo: { bar: { baz: { qux: { value: 42 } } } } });
|
||||
expect(result).toStrictEqual({
|
||||
foo: { bar: { baz: { qux: { value: 42 } } } },
|
||||
});
|
||||
});
|
||||
|
||||
it('should handle JSON input that contains escaped characters', () => {
|
||||
const jsonString = '{"name": "John\\", \\"Doe", "age": 30}';
|
||||
const result = recursiveParseJSON(jsonString);
|
||||
expect(result).toEqual({ name: 'John", "Doe', age: 30 });
|
||||
expect(result).toStrictEqual({ name: 'John", "Doe', age: 30 });
|
||||
});
|
||||
});
|
||||
|
||||
@@ -72,14 +74,14 @@ describe('flattenObject in the objects recursively', () => {
|
||||
f: 4,
|
||||
};
|
||||
|
||||
expect(flattenObject(nestedObj)).toEqual(expected);
|
||||
expect(flattenObject(nestedObj)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should return an empty object when input is empty', () => {
|
||||
const nestedObj = {};
|
||||
const expected = {};
|
||||
|
||||
expect(flattenObject(nestedObj)).toEqual(expected);
|
||||
expect(flattenObject(nestedObj)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle non-nested objects correctly', () => {
|
||||
@@ -94,7 +96,7 @@ describe('flattenObject in the objects recursively', () => {
|
||||
c: 3,
|
||||
};
|
||||
|
||||
expect(flattenObject(nestedObj)).toEqual(expected);
|
||||
expect(flattenObject(nestedObj)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle null and undefined correctly', () => {
|
||||
@@ -107,7 +109,7 @@ describe('flattenObject in the objects recursively', () => {
|
||||
b: undefined,
|
||||
};
|
||||
|
||||
expect(flattenObject(nestedObj)).toEqual(expected);
|
||||
expect(flattenObject(nestedObj)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle arrays correctly', () => {
|
||||
@@ -120,7 +122,7 @@ describe('flattenObject in the objects recursively', () => {
|
||||
b: 2,
|
||||
};
|
||||
|
||||
expect(flattenObject(objWithArray)).toEqual(expected);
|
||||
expect(flattenObject(objWithArray)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle nested objects in arrays correctly', () => {
|
||||
@@ -133,7 +135,7 @@ describe('flattenObject in the objects recursively', () => {
|
||||
d: 3,
|
||||
};
|
||||
|
||||
expect(flattenObject(objWithArray)).toEqual(expected);
|
||||
expect(flattenObject(objWithArray)).toStrictEqual(expected);
|
||||
});
|
||||
|
||||
it('should handle objects with arrays and nested objects correctly', () => {
|
||||
@@ -150,7 +152,7 @@ describe('flattenObject in the objects recursively', () => {
|
||||
e: 5,
|
||||
};
|
||||
|
||||
expect(flattenObject(complexObj)).toEqual(expected);
|
||||
expect(flattenObject(complexObj)).toStrictEqual(expected);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -287,7 +287,7 @@ export const aggregateAttributesResourcesToString = (logData: ILog): string => {
|
||||
outputJson.scope = outputJson.scope || {};
|
||||
Object.assign(outputJson.scope, logData[key as keyof ILog]);
|
||||
} else {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
outputJson[key] = logData[key as keyof ILog];
|
||||
}
|
||||
});
|
||||
|
||||
@@ -256,7 +256,7 @@ describe('LogExplorerQuerySection', () => {
|
||||
|
||||
VIEWS_TO_TEST.forEach((view) => {
|
||||
rerender(<LogExplorerQuerySection selectedView={view} />);
|
||||
expect(mockQueryBuilderContext.currentQuery).toEqual(initialQuery);
|
||||
expect(mockQueryBuilderContext.currentQuery).toStrictEqual(initialQuery);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -350,7 +350,7 @@ describe('useInitialQuery - Priority-Based Resource Filtering', () => {
|
||||
const serviceItems = calledWith.items.filter(
|
||||
(item: TagFilterItem) => item.key?.key === 'service.name',
|
||||
);
|
||||
expect(serviceItems.length).toBe(1);
|
||||
expect(serviceItems).toHaveLength(1);
|
||||
|
||||
// Verify no priority items (k8s, cloud, host, container) are included
|
||||
const priorityItems = calledWith.items.filter(
|
||||
|
||||
@@ -255,7 +255,7 @@ describe.skip('LogsExplorerViews Pagination', () => {
|
||||
expect(
|
||||
screen.queryByText('pending_data_placeholder'),
|
||||
).not.toBeInTheDocument();
|
||||
expect(capturedPayloads.length).toBe(1);
|
||||
expect(capturedPayloads).toHaveLength(1);
|
||||
});
|
||||
|
||||
// Verify the payload of the first call, expecting offset 0
|
||||
@@ -285,7 +285,7 @@ describe.skip('LogsExplorerViews Pagination', () => {
|
||||
// Verify the second page request was made
|
||||
// Wait for the second API call to be captured after the scroll
|
||||
await waitFor(() => {
|
||||
expect(capturedPayloads.length).toBe(2);
|
||||
expect(capturedPayloads).toHaveLength(2);
|
||||
});
|
||||
|
||||
// Store the time range from the first payload, which should be consistent in subsequent requests
|
||||
@@ -324,7 +324,7 @@ describe.skip('LogsExplorerViews Pagination', () => {
|
||||
// Verify the third page request was made
|
||||
// Wait for the third API call to be captured
|
||||
await waitFor(() => {
|
||||
expect(capturedPayloads.length).toBe(3);
|
||||
expect(capturedPayloads).toHaveLength(3);
|
||||
});
|
||||
const thirdPayload = capturedPayloads[2];
|
||||
// Verify the payload of the third call, expecting offset 200 and consistent time range
|
||||
@@ -526,13 +526,13 @@ describe('Logs Explorer -> stage and run query', () => {
|
||||
const secondPayload = capturedPayloads[capturedPayloads.length - 1];
|
||||
|
||||
// Verify that the timestamps have changed due to UpdateTimeInterval
|
||||
expect(secondPayload.start).not.toEqual(initialStart);
|
||||
expect(secondPayload.end).not.toEqual(initialEnd);
|
||||
expect(secondPayload.start).not.toStrictEqual(initialStart);
|
||||
expect(secondPayload.end).not.toStrictEqual(initialEnd);
|
||||
|
||||
// The timestamps should be different (the exact difference depends on the mock implementation)
|
||||
// Note: The timestamps might go backwards if UpdateTimeInterval is not called properly
|
||||
expect(secondPayload.start).not.toEqual(initialStart);
|
||||
expect(secondPayload.end).not.toEqual(initialEnd);
|
||||
expect(secondPayload.start).not.toStrictEqual(initialStart);
|
||||
expect(secondPayload.end).not.toStrictEqual(initialEnd);
|
||||
|
||||
// Verify that the IDs have changed (this confirms the Stage & Run Query button worked)
|
||||
expect(currentStagedQuery.id).not.toBe(initialStagedQueryId);
|
||||
|
||||
@@ -183,7 +183,7 @@ describe('LogsExplorerViews -', () => {
|
||||
// Test that the menu items are present
|
||||
const expectedMenuItemsCount = 3;
|
||||
const menuItems = document.querySelectorAll('.menu-items .item');
|
||||
expect(menuItems.length).toBe(expectedMenuItemsCount);
|
||||
expect(menuItems).toHaveLength(expectedMenuItemsCount);
|
||||
|
||||
// Test that the component renders without crashing
|
||||
expect(queryByTestId(periscopeDownloadButtonTestId)).toBeInTheDocument();
|
||||
@@ -429,7 +429,7 @@ describe('LogsExplorerViews -', () => {
|
||||
expect(first.groupBy?.length ?? 0).toBe(0);
|
||||
expect(first.having?.expression).toBe('');
|
||||
// Default orderBy should be timestamp desc, then id desc
|
||||
expect(first.orderBy).toEqual([
|
||||
expect(first.orderBy).toStrictEqual([
|
||||
{ columnName: 'timestamp', order: 'desc' },
|
||||
{ columnName: 'id', order: 'desc' },
|
||||
]);
|
||||
|
||||
@@ -135,8 +135,8 @@ describe('MembersSettings (integration)', () => {
|
||||
|
||||
await user.click(screen.getByRole('button', { name: /invite member/i }));
|
||||
|
||||
expect(await screen.findAllByPlaceholderText('john@signoz.io')).toHaveLength(
|
||||
3,
|
||||
);
|
||||
await expect(
|
||||
screen.findAllByPlaceholderText('john@signoz.io'),
|
||||
).resolves.toHaveLength(3);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -164,7 +164,7 @@ describe('TopOperation API Integration', () => {
|
||||
// Verify that only the top_operations endpoint was called
|
||||
expect(apiCalls).toHaveLength(1);
|
||||
expect(apiCalls[0].endpoint).toBe(TOP_OPERATIONS_ENDPOINT);
|
||||
expect(apiCalls[0].body).toEqual({
|
||||
expect(apiCalls[0].body).toStrictEqual({
|
||||
start: `${defaultApiCallExpectation.start}`,
|
||||
end: `${defaultApiCallExpectation.end}`,
|
||||
service: defaultApiCallExpectation.service,
|
||||
@@ -198,7 +198,7 @@ describe('TopOperation API Integration', () => {
|
||||
// Verify that the entry_point_operations endpoint was called
|
||||
expect(apiCalls).toHaveLength(1);
|
||||
expect(apiCalls[0].endpoint).toBe(ENTRY_POINT_OPERATIONS_ENDPOINT);
|
||||
expect(apiCalls[0].body).toEqual({
|
||||
expect(apiCalls[0].body).toStrictEqual({
|
||||
start: `${defaultApiCallExpectation.start}`,
|
||||
end: `${defaultApiCallExpectation.end}`,
|
||||
service: defaultApiCallExpectation.service,
|
||||
|
||||
@@ -7,7 +7,7 @@ import {
|
||||
} from './utils';
|
||||
|
||||
describe('Error Rate', () => {
|
||||
test('should return correct error rate', () => {
|
||||
it('should return correct error rate', () => {
|
||||
const list: TopOperationList = getTopOperationList({
|
||||
errorCount: 10,
|
||||
numCalls: 100,
|
||||
@@ -16,35 +16,35 @@ describe('Error Rate', () => {
|
||||
expect(getErrorRate(list)).toBe(10);
|
||||
});
|
||||
|
||||
test('should handle no errors gracefully', () => {
|
||||
it('should handle no errors gracefully', () => {
|
||||
const list = getTopOperationList({ errorCount: 0, numCalls: 100 });
|
||||
expect(getErrorRate(list)).toBe(0);
|
||||
});
|
||||
|
||||
test('should handle zero calls', () => {
|
||||
it('should handle zero calls', () => {
|
||||
const list = getTopOperationList({ errorCount: 0, numCalls: 0 });
|
||||
expect(getErrorRate(list)).toBe(0);
|
||||
});
|
||||
});
|
||||
|
||||
describe('getNearestHighestBucketValue', () => {
|
||||
test('should return nearest higher bucket value', () => {
|
||||
it('should return nearest higher bucket value', () => {
|
||||
expect(getNearestHighestBucketValue(50, [10, 20, 30, 40, 60, 70])).toBe('60');
|
||||
});
|
||||
|
||||
test('should return +Inf for value higher than any bucket', () => {
|
||||
it('should return +Inf for value higher than any bucket', () => {
|
||||
expect(getNearestHighestBucketValue(80, [10, 20, 30, 40, 60, 70])).toBe(
|
||||
'+Inf',
|
||||
);
|
||||
});
|
||||
|
||||
test('should return the first bucket for value lower than all buckets', () => {
|
||||
it('should return the first bucket for value lower than all buckets', () => {
|
||||
expect(getNearestHighestBucketValue(5, [10, 20, 30, 40, 60, 70])).toBe('10');
|
||||
});
|
||||
});
|
||||
|
||||
describe('convertedTracesToDownloadData', () => {
|
||||
test('should convert trace data correctly', () => {
|
||||
it('should convert trace data correctly', () => {
|
||||
const data = [
|
||||
{
|
||||
name: 'op1',
|
||||
@@ -56,7 +56,7 @@ describe('convertedTracesToDownloadData', () => {
|
||||
},
|
||||
];
|
||||
|
||||
expect(convertedTracesToDownloadData(data)).toEqual([
|
||||
expect(convertedTracesToDownloadData(data)).toStrictEqual([
|
||||
{
|
||||
Name: 'op1',
|
||||
'P50 (in ms)': '50.00',
|
||||
|
||||
@@ -130,7 +130,9 @@ describe('TimeSeries', () => {
|
||||
const alertIcon = screen.getByRole('img', { name: 'no unit warning' });
|
||||
await user.hover(alertIcon);
|
||||
|
||||
expect(await screen.findByText('metric details')).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('metric details'),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('shows save unit prompt with enabled button when metric has no unit and a unit is selected', async () => {
|
||||
@@ -142,9 +144,9 @@ describe('TimeSeries', () => {
|
||||
showYAxisUnitSelector: true,
|
||||
});
|
||||
|
||||
expect(
|
||||
await screen.findByText('Set the selected unit as the metric unit?'),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText('Set the selected unit as the metric unit?'),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const yesButton = screen.getByRole('button', { name: 'Yes' });
|
||||
expect(yesButton).toBeEnabled();
|
||||
|
||||
@@ -61,24 +61,24 @@ describe('splitQueryIntoOneChartPerQuery', () => {
|
||||
expect(result).toHaveLength(4);
|
||||
// Verify query 1 has the correct data
|
||||
expect(result[0].builder.queryData).toHaveLength(1);
|
||||
expect(result[0].builder.queryData[0]).toEqual(MOCK_QUERY_DATA_1);
|
||||
expect(result[0].builder.queryData[0]).toStrictEqual(MOCK_QUERY_DATA_1);
|
||||
expect(result[0].builder.queryFormulas).toHaveLength(0);
|
||||
expect(result[0].unit).toBeUndefined();
|
||||
// Verify query 2 has the correct data
|
||||
expect(result[1].builder.queryData).toHaveLength(1);
|
||||
expect(result[1].builder.queryData[0]).toEqual(MOCK_QUERY_DATA_2);
|
||||
expect(result[1].builder.queryData[0]).toStrictEqual(MOCK_QUERY_DATA_2);
|
||||
expect(result[1].builder.queryFormulas).toHaveLength(0);
|
||||
expect(result[1].unit).toBe('unit2');
|
||||
// Verify query 3 has the correct data
|
||||
expect(result[2].builder.queryFormulas).toHaveLength(1);
|
||||
expect(result[2].builder.queryFormulas[0]).toEqual(MOCK_FORMULA_DATA);
|
||||
expect(result[2].builder.queryFormulas[0]).toStrictEqual(MOCK_FORMULA_DATA);
|
||||
expect(result[2].builder.queryData).toHaveLength(2); // 2 disabled queries
|
||||
expect(result[2].builder.queryData[0].disabled).toBe(true);
|
||||
expect(result[2].builder.queryData[1].disabled).toBe(true);
|
||||
expect(result[2].unit).toBe('');
|
||||
// Verify query 4 has the correct data
|
||||
expect(result[3].builder.queryFormulas).toHaveLength(1);
|
||||
expect(result[3].builder.queryFormulas[0]).toEqual(MOCK_FORMULA_DATA);
|
||||
expect(result[3].builder.queryFormulas[0]).toStrictEqual(MOCK_FORMULA_DATA);
|
||||
expect(result[3].builder.queryData).toHaveLength(2); // 2 disabled queries
|
||||
expect(result[3].builder.queryData[0].disabled).toBe(true);
|
||||
expect(result[3].builder.queryData[1].disabled).toBe(true);
|
||||
@@ -106,7 +106,7 @@ describe('useGetMetrics', () => {
|
||||
const { result } = renderHook(() => useGetMetrics(['metric1']));
|
||||
expect(result.current.metrics).toHaveLength(1);
|
||||
expect(result.current.metrics[0]).toBeDefined();
|
||||
expect(result.current.metrics[0]).toEqual(MOCK_METRIC_METADATA);
|
||||
expect(result.current.metrics[0]).toStrictEqual(MOCK_METRIC_METADATA);
|
||||
expect(result.current.isLoading).toBe(false);
|
||||
expect(result.current.isError).toBe(false);
|
||||
});
|
||||
@@ -131,7 +131,7 @@ describe('getMetricUnits', () => {
|
||||
it('should return the same unit for units that are not known to the universal unit mapper', () => {
|
||||
const result = getMetricUnits([MOCK_METRIC_METADATA]);
|
||||
expect(result).toHaveLength(1);
|
||||
expect(result[0]).toEqual(MOCK_METRIC_METADATA.unit);
|
||||
expect(result[0]).toStrictEqual(MOCK_METRIC_METADATA.unit);
|
||||
});
|
||||
|
||||
it('should return universal unit for units that are known to the universal unit mapper', () => {
|
||||
|
||||
@@ -157,7 +157,7 @@ describe('ContextLinks Component', () => {
|
||||
|
||||
// Test the function by calling it with the current state
|
||||
const result = setContextLinksCall(MOCK_EMPTY_CONTEXT_LINKS);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
linksData: [
|
||||
{
|
||||
id: expect.any(String), // ID is generated dynamically
|
||||
|
||||
@@ -93,7 +93,7 @@ jest.mock('react-router-dom-v5-compat', () => ({
|
||||
describe('placeWidgetAtBottom', () => {
|
||||
it('should place widget at (0,0) when layout is empty', () => {
|
||||
const result = placeWidgetAtBottom('widget1', []);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget1',
|
||||
x: 0,
|
||||
y: 0,
|
||||
@@ -104,7 +104,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
|
||||
it('should place widget at (0,0) with custom dimensions when layout is empty', () => {
|
||||
const result = placeWidgetAtBottom('widget1', [], 4, 8);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget1',
|
||||
x: 0,
|
||||
y: 0,
|
||||
@@ -116,7 +116,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
it('should place widget next to existing widget in last row if space available', () => {
|
||||
const existingLayout = [{ i: 'widget1', x: 0, y: 0, w: 6, h: 6 }];
|
||||
const result = placeWidgetAtBottom('widget2', existingLayout);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget2',
|
||||
x: 6,
|
||||
y: 0,
|
||||
@@ -131,7 +131,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
{ i: 'widget2', x: 6, y: 0, w: 6, h: 6 },
|
||||
];
|
||||
const result = placeWidgetAtBottom('widget3', existingLayout);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget3',
|
||||
x: 0,
|
||||
y: 6,
|
||||
@@ -147,7 +147,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
{ i: 'widget3', x: 0, y: 6, w: 6, h: 6 },
|
||||
];
|
||||
const result = placeWidgetAtBottom('widget4', existingLayout);
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget4',
|
||||
x: 6,
|
||||
y: 6,
|
||||
@@ -163,7 +163,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
];
|
||||
const result = placeWidgetAtBottom('widget3', existingLayout);
|
||||
// y = 2 here as later the react-grid-layout will add 2px to the y value while adjusting the layout
|
||||
expect(result).toEqual({
|
||||
expect(result).toStrictEqual({
|
||||
i: 'widget3',
|
||||
x: 6,
|
||||
y: 2,
|
||||
@@ -176,7 +176,7 @@ describe('placeWidgetAtBottom', () => {
|
||||
describe('placeWidgetBetweenRows', () => {
|
||||
it('should return single widget layout when layout is empty', () => {
|
||||
const result = placeWidgetBetweenRows('widget1', [], 'currentRow');
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
i: 'widget1',
|
||||
x: 0,
|
||||
@@ -195,7 +195,7 @@ describe('placeWidgetBetweenRows', () => {
|
||||
|
||||
const result = placeWidgetBetweenRows('widget3', existingLayout, 'widget2');
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{ i: 'widget1', x: 0, y: 0, w: 6, h: 6 },
|
||||
{ i: 'widget2', x: 6, y: 0, w: 6, h: 6 },
|
||||
{ i: 'widget3', x: 0, y: 6, w: 6, h: 6 },
|
||||
@@ -238,7 +238,7 @@ describe('placeWidgetBetweenRows', () => {
|
||||
'widget3',
|
||||
);
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{
|
||||
h: 1,
|
||||
i: "'widget1'",
|
||||
@@ -292,7 +292,7 @@ describe('placeWidgetBetweenRows', () => {
|
||||
3,
|
||||
);
|
||||
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
{ i: 'widget1', x: 0, y: 0, w: 12, h: 4 },
|
||||
{ i: 'widget2', x: 0, y: 4, w: 8, h: 3 },
|
||||
]);
|
||||
|
||||
@@ -12,7 +12,7 @@ describe('getUplotChartData', () => {
|
||||
BarNonStackedChartData.fillSpans,
|
||||
BarNonStackedChartData.stackedBarChart,
|
||||
);
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
[1758713940, 1758715020],
|
||||
[33.933, 31.767],
|
||||
[20.0, 25.0],
|
||||
@@ -29,10 +29,10 @@ describe('getUplotChartData', () => {
|
||||
// First series: [33.933, 31.767] + [20.0, 25.0] = [53.933, 56.767]
|
||||
// Second series: [20.0, 25.0] (unchanged)
|
||||
expect(result).toHaveLength(3);
|
||||
expect(result[0]).toEqual([1758713940, 1758715020]);
|
||||
expect(result[0]).toStrictEqual([1758713940, 1758715020]);
|
||||
expect(result[1][0]).toBeCloseTo(53.933, 3);
|
||||
expect(result[1][1]).toBeCloseTo(56.767, 3);
|
||||
expect(result[2]).toEqual([20.0, 25.0]);
|
||||
expect(result[2]).toStrictEqual([20.0, 25.0]);
|
||||
});
|
||||
|
||||
it('should return the correct chart data for time series chart', () => {
|
||||
@@ -41,7 +41,7 @@ describe('getUplotChartData', () => {
|
||||
TimeSeriesChartData.fillSpans,
|
||||
TimeSeriesChartData.stackedBarChart,
|
||||
);
|
||||
expect(result).toEqual([
|
||||
expect(result).toStrictEqual([
|
||||
[1758713940, 1758715020],
|
||||
[33.933, 31.767],
|
||||
[20.0, 25.0],
|
||||
|
||||
@@ -38,7 +38,7 @@ const buildSupersetQuery = (extras?: Record<string, unknown>): Query => ({
|
||||
});
|
||||
|
||||
describe('handleQueryChange', () => {
|
||||
test('sets list-specific fields when switching to LIST', () => {
|
||||
it('sets list-specific fields when switching to LIST', () => {
|
||||
const superset = buildSupersetQuery();
|
||||
const output = handleQueryChange(
|
||||
PANEL_TYPES.LIST as keyof PartialPanelTypes,
|
||||
@@ -60,7 +60,7 @@ describe('handleQueryChange', () => {
|
||||
expect(secondQuery.queryName).toBe('B');
|
||||
});
|
||||
|
||||
test('resets noop and pagination when leaving LIST', () => {
|
||||
it('resets noop and pagination when leaving LIST', () => {
|
||||
const superset = buildSupersetQuery({
|
||||
aggregateOperator: 'noop',
|
||||
offset: 5,
|
||||
|
||||
@@ -86,9 +86,9 @@ export default function MarkdownStep(): JSX.Element {
|
||||
} else if (selectedModule?.id === ModulesMap.AzureMonitoring) {
|
||||
docFilePaths = AzureMonitoringDocFilePaths;
|
||||
}
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
if (docFilePaths && docFilePaths[path]) {
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
setMarkdownContent(docFilePaths[path]);
|
||||
}
|
||||
|
||||
|
||||
@@ -391,7 +391,7 @@ export const getSupportedFrameworks = ({
|
||||
return [];
|
||||
}
|
||||
|
||||
// @ts-ignore
|
||||
// @ts-expect-error
|
||||
return frameworksMap[moduleID][dataSourceName];
|
||||
};
|
||||
|
||||
|
||||
@@ -103,9 +103,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
const othersCheckbox = screen.getByLabelText(/^others$/i);
|
||||
await user.click(othersCheckbox);
|
||||
|
||||
expect(
|
||||
await screen.findByPlaceholderText(/what tool do you currently use/i),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByPlaceholderText(/what tool do you currently use/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('shows migration timeline options only when specific observability tools are selected', async () => {
|
||||
@@ -120,9 +120,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
const datadogCheckbox = screen.getByLabelText(/datadog/i);
|
||||
await user.click(datadogCheckbox);
|
||||
|
||||
expect(
|
||||
await screen.findByText(/What is your timeline for migrating to SigNoz/i),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/What is your timeline for migrating to SigNoz/i),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
// Not visible when None is selected
|
||||
const noneCheckbox = screen.getByLabelText(/none\/starting fresh/i);
|
||||
@@ -144,9 +144,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
const nextButton = screen.getByRole('button', { name: /next/i });
|
||||
await user.click(nextButton);
|
||||
|
||||
expect(
|
||||
await screen.findByText(/how did you first come across signoz/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/how did you first come across signoz/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -162,12 +162,12 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/just exploring/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByText(/set up your workspace/i, {}),
|
||||
).toBeInTheDocument();
|
||||
expect(
|
||||
await screen.findByText(/how did you first come across signoz/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/set up your workspace/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/how did you first come across signoz/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('disables next button when fields are empty', async () => {
|
||||
@@ -198,9 +198,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/just exploring/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const discoverInput = screen.getByPlaceholderText(/e\.g\., googling/i);
|
||||
await user.type(discoverInput, 'Found via Google search');
|
||||
@@ -225,19 +225,16 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/just exploring/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByText(/what got you interested in signoz/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/what got you interested in signoz/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
const othersCheckbox = screen.getByLabelText(/^others$/i);
|
||||
await user.click(othersCheckbox);
|
||||
|
||||
expect(
|
||||
await screen.findByPlaceholderText(
|
||||
/what got you interested in signoz/i,
|
||||
{},
|
||||
),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByPlaceholderText(/what got you interested in signoz/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -253,9 +250,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/just exploring/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
await user.type(
|
||||
screen.getByPlaceholderText(/e\.g\., googling/i),
|
||||
@@ -264,16 +261,15 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/lowering observability costs/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByText(
|
||||
/what does your scale approximately look like/i,
|
||||
{},
|
||||
),
|
||||
).toBeInTheDocument();
|
||||
expect(await screen.findByText(/logs \/ day/i, {})).toBeInTheDocument();
|
||||
expect(
|
||||
await screen.findByText(/number of services/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/what does your scale approximately look like/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/logs \/ day/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByText(/number of services/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('fires PUT to /zeus/profiles and advances to step 4 on success', async () => {
|
||||
@@ -327,9 +323,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/just exploring/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByPlaceholderText(/e\.g\., googling/i, {}),
|
||||
).resolves.toBeInTheDocument();
|
||||
|
||||
await user.type(
|
||||
screen.getByPlaceholderText(/e\.g\., googling/i),
|
||||
@@ -338,9 +334,9 @@ describe('OnboardingQuestionaire Component', () => {
|
||||
await user.click(screen.getByLabelText(/lowering observability costs/i));
|
||||
await user.click(screen.getByRole('button', { name: /next/i }));
|
||||
|
||||
expect(
|
||||
await screen.findByRole('button', { name: /i'll do this later/i }),
|
||||
).toBeInTheDocument();
|
||||
await expect(
|
||||
screen.findByRole('button', { name: /i'll do this later/i }),
|
||||
).resolves.toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user