From 90f809c2fb1e9aea697652a71ee374534e055aeb Mon Sep 17 00:00:00 2001 From: David Tai Date: Sun, 29 Jan 2023 18:02:12 +0800 Subject: [PATCH 1/2] update `createRegExp` function --- src/core/types/escape.ts | 2 +- src/index.ts | 36 +++++++++++++++++++++++------------- 2 files changed, 24 insertions(+), 14 deletions(-) diff --git a/src/core/types/escape.ts b/src/core/types/escape.ts index e1ccee45..142e24c7 100644 --- a/src/core/types/escape.ts +++ b/src/core/types/escape.ts @@ -20,7 +20,7 @@ export type EscapeChar = Escape export type StripEscapes = T extends `${infer A}\\${infer B}` ? `${A}${B}` : T // prettier-ignore -type ExactEscapeChar = '.' | '*' | '+' | '?' | '^' | '$' | '{' | '}' | '(' | ')' | '|' | '[' | ']' | '/' +export type ExactEscapeChar = '.' | '*' | '+' | '?' | '^' | '$' | '{' | '}' | '(' | ')' | '|' | '[' | ']' | '/' export type GetValue = T extends string ? Escape diff --git a/src/index.ts b/src/index.ts index 4d0d66d8..a579bdfe 100644 --- a/src/index.ts +++ b/src/index.ts @@ -3,21 +3,31 @@ import { Input, exactly } from './core/inputs' import type { Join } from './core/types/join' import type { MagicRegExp, MagicRegExpMatchArray } from './core/types/magic-regexp' -export const createRegExp = < - Value extends string, - NamedGroups extends string = never, - CapturedGroupsArr extends (string | undefined)[] = [], - Flags extends Flag[] = never[] ->( - raw: Input | Value, - flags?: [...Flags] | string | Set -) => - new RegExp(exactly(raw).toString(), [...(flags || '')].join('')) as MagicRegExp< - `/${Value}/${Join}`, - NamedGroups, - CapturedGroupsArr, +import type { Escape, ExactEscapeChar } from './core/types/escape' + +export const createRegExp: { + /** Create Magic RegExp from Input helper */ + < + Value extends string, + NamedGroups extends string = never, + CapturedGroupsArr extends (string | undefined)[] = [], + Flags extends Flag[] = never[] + >( + raw: Input, + flags?: [...Flags] | string | Set + ): MagicRegExp<`/${Value}/${Join}`, NamedGroups, CapturedGroupsArr, Flags[number]> + /** Create Magic RegExp from string, string will be sanitized */ + ( + raw: Value, + flags?: [...Flags] | string | Set + ): MagicRegExp< + `/${Escape}/${Join}`, + never, + [], Flags[number] > +} = (raw: any, flags?: any) => + new RegExp(exactly(raw).toString(), [...(flags || '')].join('')) as any export * from './core/flags' export * from './core/inputs' From 28a0cbedee29911869248a07289389a4bbf2ad07 Mon Sep 17 00:00:00 2001 From: David Tai Date: Sun, 29 Jan 2023 18:02:52 +0800 Subject: [PATCH 2/2] add/update (type) tests --- test/index.test.ts | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/test/index.test.ts b/test/index.test.ts index 58f88ed3..cba96c59 100644 --- a/test/index.test.ts +++ b/test/index.test.ts @@ -26,7 +26,17 @@ describe('magic-regexp', () => { }) it('collects flag type', () => { const re = createRegExp('.', [global, multiline]) - expectTypeOf(re).toEqualTypeOf>() + expectTypeOf(re).toEqualTypeOf>() + }) + it('sanitize string input', () => { + const escapeChars = '.*+?^${}()[]/' + const re = createRegExp(escapeChars) + expect(String(re)).toMatchInlineSnapshot( + '"/\\\\.\\\\*\\\\+\\\\?\\\\^\\\\$\\\\{\\\\}\\\\(\\\\)\\\\[\\\\]\\\\//"' + ) + expectTypeOf(re).toEqualTypeOf< + MagicRegExp<'/\\.\\*\\+\\?\\^\\$\\{\\}\\(\\)\\[\\]\\//', never, []> + >() }) })