Skip to content

Commit e9ff0cd

Browse files
committed
Add test for empty string
1 parent 4d8596d commit e9ff0cd

File tree

1 file changed

+37
-19
lines changed

1 file changed

+37
-19
lines changed

packages/remark-lsx/src/server/routes/list-pages/index.spec.ts

Lines changed: 37 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -265,10 +265,10 @@ describe('when excludedPaths is handled', () => {
265265
builderMock.query = queryMock;
266266

267267
beforeEach(() => {
268+
vi.clearAllMocks();
268269
mocks.generateBaseQueryMock.mockResolvedValue(builderMock);
269270
queryMock.and.mockReturnValue(queryMock);
270271

271-
// Setup successful flow for count and exec
272272
const queryClonedMock = mock<PageQuery>();
273273
queryMock.clone.mockReturnValue(queryClonedMock);
274274
queryClonedMock.count.mockResolvedValue(0);
@@ -279,45 +279,63 @@ describe('when excludedPaths is handled', () => {
279279
mocks.getToppageViewersCountMock.mockResolvedValue(0);
280280
});
281281

282-
it('does not add path exclusion conditions when excludedPaths is empty', async () => {
283-
// setup
282+
it('adds a sanitized regex exclusion condition with non-capturing groups', async () => {
284283
const reqMock = mock<IListPagesRequest>();
285284
reqMock.query = { pagePath };
286285
const resMock = mock<Response>();
287286
resMock.status.mockReturnValue(mock<Response>());
288287

289-
// excludedPaths is empty
290-
const handler = listPages({ excludedPaths: [] });
288+
// Includes a path with meta-characters to test sanitization
289+
const excludedPaths = ['/user', 'tmp.bak'];
290+
const handler = listPages({ excludedPaths });
291291
await handler(reqMock, resMock);
292292

293-
// query.and should NOT be called with a $not regex for paths
294-
expect(queryMock.and).not.toHaveBeenCalledWith(
295-
expect.arrayContaining([
296-
expect.objectContaining({
297-
path: expect.objectContaining({ $not: expect.any(RegExp) }),
298-
}),
299-
]),
300-
);
293+
// Matches the updated logic: non-capturing groups and escaped dots
294+
const expectedRegex = /^\/(?:user|tmp\.bak)(?:\/|$)/;
295+
expect(queryMock.and).toHaveBeenCalledWith([
296+
{
297+
path: { $not: expectedRegex },
298+
},
299+
]);
301300
});
302301

303-
it('adds a regex exclusion condition when excludedPaths is specified', async () => {
304-
// setup
302+
it('filters out empty paths to prevent invalid regex or broad exclusion', async () => {
305303
const reqMock = mock<IListPagesRequest>();
306304
reqMock.query = { pagePath };
307305
const resMock = mock<Response>();
308306
resMock.status.mockReturnValue(mock<Response>());
309307

310-
// excludedPaths provided
311-
const excludedPaths = ['/user', '/tmp'];
308+
// Input contains a slash (which becomes empty after cleaning) and an empty string
309+
const excludedPaths = ['/', '', '/valid'];
312310
const handler = listPages({ excludedPaths });
313311
await handler(reqMock, resMock);
314312

315-
// check if the logic generates the correct regex: ^\/(user|tmp)(\/|$)
316-
const expectedRegex = /^\/(user|tmp)(\/|$)/;
313+
// The regex should only contain 'valid'
314+
const expectedRegex = /^\/(?:valid)(?:\/|$)/;
315+
317316
expect(queryMock.and).toHaveBeenCalledWith([
318317
{
319318
path: { $not: expectedRegex },
320319
},
321320
]);
322321
});
322+
323+
it('does not call query.and if all provided excludedPaths are empty strings', async () => {
324+
const reqMock = mock<IListPagesRequest>();
325+
reqMock.query = { pagePath };
326+
const resMock = mock<Response>();
327+
resMock.status.mockReturnValue(mock<Response>());
328+
329+
const handler = listPages({ excludedPaths: ['/', ''] });
330+
await handler(reqMock, resMock);
331+
332+
// Should behave like the empty array case
333+
expect(queryMock.and).not.toHaveBeenCalledWith(
334+
expect.arrayContaining([
335+
expect.objectContaining({
336+
path: expect.objectContaining({ $not: expect.any(RegExp) }),
337+
}),
338+
]),
339+
);
340+
});
323341
});

0 commit comments

Comments
 (0)