From d01e54dea4b853d0110f41adcb7d544abd33c8fd Mon Sep 17 00:00:00 2001 From: Kristiyan Kostadinov Date: Thu, 25 Dec 2025 14:07:40 +0200 Subject: [PATCH] refactor(compiler): tokenize => Adds some logic to tokenize the `=>` character combination in the lexer. --- .../compiler/src/expression_parser/lexer.ts | 28 +++++++++++++------ .../test/expression_parser/lexer_spec.ts | 24 ++++++++++++++++ 2 files changed, 44 insertions(+), 8 deletions(-) diff --git a/packages/compiler/src/expression_parser/lexer.ts b/packages/compiler/src/expression_parser/lexer.ts index f18bfc276af..c91bf800cea 100644 --- a/packages/compiler/src/expression_parser/lexer.ts +++ b/packages/compiler/src/expression_parser/lexer.ts @@ -343,15 +343,9 @@ class _Scanner { case chars.$GT: return this.scanComplexOperator(start, String.fromCharCode(peek), chars.$EQ, '='); case chars.$BANG: + return this.scanComplexOperator(start, '!', chars.$EQ, '=', chars.$EQ, '='); case chars.$EQ: - return this.scanComplexOperator( - start, - String.fromCharCode(peek), - chars.$EQ, - '=', - chars.$EQ, - '=', - ); + return this.scanEquals(start); case chars.$AMPERSAND: return this.scanComplexOperator(start, '&', chars.$AMPERSAND, '&', chars.$EQ, '='); case chars.$BAR: @@ -424,6 +418,24 @@ class _Scanner { return newOperatorToken(start, this.index, str); } + private scanEquals(start: number): Token { + this.advance(); + let str: string = '='; + if (this.peek === chars.$EQ) { + this.advance(); + str += '='; + } else if (this.peek === chars.$GT) { + this.advance(); + str += '>'; + return newOperatorToken(start, this.index, str); + } + if (this.peek === chars.$EQ) { + this.advance(); + str += '='; + } + return newOperatorToken(start, this.index, str); + } + private scanIdentifier(): Token { const start: number = this.index; this.advance(); diff --git a/packages/compiler/test/expression_parser/lexer_spec.ts b/packages/compiler/test/expression_parser/lexer_spec.ts index 31cbbba80a2..00ebb071202 100644 --- a/packages/compiler/test/expression_parser/lexer_spec.ts +++ b/packages/compiler/test/expression_parser/lexer_spec.ts @@ -967,6 +967,30 @@ describe('lexer', () => { 'Lexer Error: Unterminated regular expression at column 2 in expression [/a]', ); }); + + it('should tokenize an arrow function without parenthesis', () => { + const tokens = lex('a => a + 1'); + expect(tokens.length).toBe(5); + expectIdentifierToken(tokens[0], 0, 1, 'a'); + expectOperatorToken(tokens[1], 2, 4, '=>'); + expectIdentifierToken(tokens[2], 5, 6, 'a'); + expectOperatorToken(tokens[3], 7, 8, '+'); + expectNumberToken(tokens[4], 9, 10, 1); + }); + + it('should tokenize an arrow function with parenthesis', () => { + const tokens = lex('(a, b) => a + b'); + expect(tokens.length).toBe(9); + expectCharacterToken(tokens[0], 0, 1, '('); + expectIdentifierToken(tokens[1], 1, 2, 'a'); + expectCharacterToken(tokens[2], 2, 3, ','); + expectIdentifierToken(tokens[3], 4, 5, 'b'); + expectCharacterToken(tokens[4], 5, 6, ')'); + expectOperatorToken(tokens[5], 7, 9, '=>'); + expectIdentifierToken(tokens[6], 10, 11, 'a'); + expectOperatorToken(tokens[7], 12, 13, '+'); + expectIdentifierToken(tokens[8], 14, 15, 'b'); + }); }); }); });