diff options
| -rw-r--r-- | src/parser/index.ts | 15 | ||||
| -rw-r--r-- | src/types.ts | 1 | ||||
| -rw-r--r-- | tests/parser.spec.ts | 104 |
3 files changed, 74 insertions, 46 deletions
diff --git a/src/parser/index.ts b/src/parser/index.ts index a336b83..7f0e945 100644 --- a/src/parser/index.ts +++ b/src/parser/index.ts @@ -129,9 +129,22 @@ const stringLiteral: Parser<Literal> = mapTo( s => Literal.String(s.join('')), ) +const REGEX_FLAGS = ['m', 'g', 'i', 'd', 's', 'u', 'y'] +const regexDelimiter = prefixed(optional(matchChar('\\')), matchChar('/')) +const regexLiteral: Parser<Literal> = mapTo( + prefixed( + regexDelimiter, + pair( + manyTill(satisfyChar(_ => true), regexDelimiter), + many0(satisfyChar(c => REGEX_FLAGS.includes(c))) + ), + ), + ([rs, flags]) => Literal.RegExp(new RegExp(rs.join(''), flags.join(''))), +) + const literalP: Parser<Literal> = delimited( whitespaces0, - or([booleanLiteral, numberLiteral, stringLiteral]), + or([booleanLiteral, numberLiteral, stringLiteral, regexLiteral]), whitespaces0, ) diff --git a/src/types.ts b/src/types.ts index dd40ce9..f02fca6 100644 --- a/src/types.ts +++ b/src/types.ts @@ -7,6 +7,7 @@ export type index = number export type Literal = Union<{ String: string + RegExp: RegExp Number: number Boolean: boolean }> diff --git a/tests/parser.spec.ts b/tests/parser.spec.ts index 13a8838..12a0bd9 100644 --- a/tests/parser.spec.ts +++ b/tests/parser.spec.ts @@ -146,51 +146,6 @@ describe('Parser', () => { ) }) - it('literals', () => { - // unsigned numbers - expect(parser(/ 0.105 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(0.105))), - ) - expect(parser(/ 9 /.source)).toEqual(wrap(Expr.Literal(Literal.Number(9)))) - expect(parser(/ 23 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(23))), - ) - - // signed numbers - expect(parser(/ 23.025 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(23.025))), - ) - expect(parser(/ -23.025 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(-23.025))), - ) - expect(parser(/ 23 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(23))), - ) - expect(parser(/ -23 /.source)).toEqual( - wrap(Expr.Literal(Literal.Number(-23))), - ) - - // boolean - expect(parser(/ true /.source)).toEqual( - wrap(Expr.Literal(Literal.Boolean(true))), - ) - expect(parser(/ false /.source)).toEqual( - wrap(Expr.Literal(Literal.Boolean(false))), - ) - - // String literal - expect(parser(/ "foobar" /.source)).toEqual( - wrap(Expr.Literal(Literal.String('foobar'))), - ) - expect(parser(/ "\nwowksadj\n\t wjksdlsd'' !@#%^(&^%$) " /.source)).toEqual( - wrap( - Expr.Literal( - Literal.String("\\nwowksadj\\n\\t wjksdlsd'' !@#%^(&^%$) "), - ), - ), - ) - }) - it('sequence of values', () => { expect(parser(/true, \s\T, \n/.source)).toEqual( wrap( @@ -204,4 +159,63 @@ describe('Parser', () => { ), ) }) + + describe('Literals', () => { + it('numbers', () => { + // unsigned numbers + expect(parser(/ 0.105 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(0.105))), + ) + expect(parser(/ 9 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(9))), + ) + expect(parser(/ 23 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(23))), + ) + + // signed numbers + expect(parser(/ 23.025 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(23.025))), + ) + expect(parser(/ -23.025 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(-23.025))), + ) + expect(parser(/ 23 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(23))), + ) + expect(parser(/ -23 /.source)).toEqual( + wrap(Expr.Literal(Literal.Number(-23))), + ) + }) + + it('boolean', () => { + expect(parser(/ true /.source)).toEqual( + wrap(Expr.Literal(Literal.Boolean(true))), + ) + expect(parser(/ false /.source)).toEqual( + wrap(Expr.Literal(Literal.Boolean(false))), + ) + }) + + it('string', () => { + expect(parser(/ "foobar" /.source)).toEqual( + wrap(Expr.Literal(Literal.String('foobar'))), + ) + expect( + parser(/ "\nwowksadj\n\t wjksdlsd'' !@#%^(&^%$) " /.source), + ).toEqual( + wrap( + Expr.Literal( + Literal.String("\\nwowksadj\\n\\t wjksdlsd'' !@#%^(&^%$) "), + ), + ), + ) + }) + + it('regex', () => { + expect(parser(/ \/^foo(bar|baz)?\/gi /.source)).toEqual( + wrap(Expr.Literal(Literal.RegExp(/^foo(bar|baz)?/gi))), + ) + }) + }) }) |
