Skip to content

Commit ca57496

Browse files
committed
Update number lexer
Ensures graphql-js matches spec after graphql/graphql-spec#56 Adds tests for changed error and success cases, fixing #68
1 parent 1a2b9f3 commit ca57496

File tree

2 files changed

+71
-15
lines changed

2 files changed

+71
-15
lines changed

src/language/__tests__/lexer.js

Lines changed: 58 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -256,6 +256,42 @@ describe('Lexer', () => {
256256
value: '0.123'
257257
});
258258

259+
expect(
260+
lexOne('123e4')
261+
).to.deep.equal({
262+
kind: TokenKind.FLOAT,
263+
start: 0,
264+
end: 5,
265+
value: '123e4'
266+
});
267+
268+
expect(
269+
lexOne('123E4')
270+
).to.deep.equal({
271+
kind: TokenKind.FLOAT,
272+
start: 0,
273+
end: 5,
274+
value: '123E4'
275+
});
276+
277+
expect(
278+
lexOne('123e-4')
279+
).to.deep.equal({
280+
kind: TokenKind.FLOAT,
281+
start: 0,
282+
end: 6,
283+
value: '123e-4'
284+
});
285+
286+
expect(
287+
lexOne('123e+4')
288+
).to.deep.equal({
289+
kind: TokenKind.FLOAT,
290+
start: 0,
291+
end: 6,
292+
value: '123e+4'
293+
});
294+
259295
expect(
260296
lexOne('-1.123e4')
261297
).to.deep.equal({
@@ -265,6 +301,15 @@ describe('Lexer', () => {
265301
value: '-1.123e4'
266302
});
267303

304+
expect(
305+
lexOne('-1.123E4')
306+
).to.deep.equal({
307+
kind: TokenKind.FLOAT,
308+
start: 0,
309+
end: 8,
310+
value: '-1.123E4'
311+
});
312+
268313
expect(
269314
lexOne('-1.123e-4')
270315
).to.deep.equal({
@@ -274,6 +319,15 @@ describe('Lexer', () => {
274319
value: '-1.123e-4'
275320
});
276321

322+
expect(
323+
lexOne('-1.123e+4')
324+
).to.deep.equal({
325+
kind: TokenKind.FLOAT,
326+
start: 0,
327+
end: 9,
328+
value: '-1.123e+4'
329+
});
330+
277331
expect(
278332
lexOne('-1.123e4567')
279333
).to.deep.equal({
@@ -295,6 +349,10 @@ describe('Lexer', () => {
295349
lexErr('1.')
296350
).to.throw('Syntax Error GraphQL (1:3) Invalid number');
297351

352+
expect(
353+
lexErr('.123')
354+
).to.throw('Syntax Error GraphQL (1:1) Unexpected character "."');
355+
298356
expect(
299357
lexErr('1.A')
300358
).to.throw('Syntax Error GraphQL (1:3) Invalid number');
@@ -303,10 +361,6 @@ describe('Lexer', () => {
303361
lexErr('-A')
304362
).to.throw('Syntax Error GraphQL (1:2) Invalid number');
305363

306-
expect(
307-
lexErr('1.0e+4')
308-
).to.throw('Syntax Error GraphQL (1:5) Invalid number');
309-
310364
expect(
311365
lexErr('1.0e')
312366
).to.throw('Syntax Error GraphQL (1:5) Invalid number');

src/language/lexer.js

Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,7 @@ function positionAfterWhitespace(body: string, startPosition: number): number {
247247
* or an int depending on whether a decimal point appears.
248248
*
249249
* Int: -?(0|[1-9][0-9]*)
250-
* Float: -?(0|[1-9][0-9]*)\.[0-9]+(e-?[0-9]+)?
250+
* Float: -?(0|[1-9][0-9]*)(\.[0-9]+)?((E|e)(+|-)?[0-9]+)?
251251
*/
252252
function readNumber(source, start, firstCode) {
253253
var code = firstCode;
@@ -280,19 +280,21 @@ function readNumber(source, start, firstCode) {
280280
} else {
281281
throw syntaxError(source, position, 'Invalid number.');
282282
}
283+
}
284+
285+
if (code === 69 || code === 101) { // E e
286+
isFloat = true;
283287

284-
if (code === 101) { // e
288+
code = charCodeAt.call(body, ++position);
289+
if (code === 43 || code === 45) { // + -
285290
code = charCodeAt.call(body, ++position);
286-
if (code === 45) { // -
291+
}
292+
if (code >= 48 && code <= 57) { // 0 - 9
293+
do {
287294
code = charCodeAt.call(body, ++position);
288-
}
289-
if (code >= 48 && code <= 57) { // 0 - 9
290-
do {
291-
code = charCodeAt.call(body, ++position);
292-
} while (code >= 48 && code <= 57); // 0 - 9
293-
} else {
294-
throw syntaxError(source, position, 'Invalid number.');
295-
}
295+
} while (code >= 48 && code <= 57); // 0 - 9
296+
} else {
297+
throw syntaxError(source, position, 'Invalid number.');
296298
}
297299
}
298300

0 commit comments

Comments
 (0)