module: correctly detect top-level await in ambiguous contexts · nodejs/node@7880978
1+import { spawnPromisified } from '../common/index.mjs';
2+import { describe, it } from 'node:test';
3+import { strictEqual, match } from 'node:assert';
4+5+describe('unusual top-level await syntax errors', () => {
6+const expressions = [
7+// string
8+{ expression: '""' },
9+// number
10+{ expression: '0' },
11+// boolean
12+{ expression: 'true' },
13+// null
14+{ expression: 'null' },
15+// undefined
16+{ expression: 'undefined' },
17+// object
18+{ expression: '{}' },
19+// array
20+{ expression: '[]' },
21+// new
22+{ expression: 'new Date()' },
23+// identifier
24+{ initialize: 'const a = 2;', expression: 'a' },
25+];
26+it('should not crash the process', async () => {
27+for (const { expression, initialize } of expressions) {
28+const wrapperExpressions = [
29+`function callAwait() {}; callAwait(await ${expression});`,
30+`if (await ${expression}) {}`,
31+`{ key: await ${expression} }`,
32+`[await ${expression}]`,
33+`(await ${expression})`,
34+];
35+for (const wrapperExpression of wrapperExpressions) {
36+const { code, signal, stdout, stderr } = await spawnPromisified(process.execPath, [
37+'--eval',
38+`
39+ ${initialize || ''}
40+ ${wrapperExpression}
41+ `,
42+]);
43+44+strictEqual(stderr, '');
45+strictEqual(stdout, '');
46+strictEqual(code, 0);
47+strictEqual(signal, null);
48+}
49+}
50+});
51+52+it('should throw the error for unrelated syntax errors', async () => {
53+const expression = 'foo bar';
54+const wrapperExpressions = [
55+[`function callSyntaxError() {}; callSyntaxError(${expression});`, /missing \) after argument list/],
56+[`if (${expression}) {}`, /Unexpected identifier/],
57+[`{ key: ${expression} }`, /Unexpected identifier/],
58+[`[${expression}]`, /Unexpected identifier/],
59+[`(${expression})`, /Unexpected identifier/],
60+[`const ${expression} = 1;`, /Missing initializer in const declaration/],
61+[`console.log('PI: ' Math.PI);`, /missing \) after argument list/],
62+[`callAwait(await "" "");`, /missing \) after argument list/],
63+];
64+65+for (const [wrapperExpression, error] of wrapperExpressions) {
66+const { code, signal, stdout, stderr } = await spawnPromisified(process.execPath, [
67+'--eval',
68+`
69+ ${wrapperExpression}
70+ `,
71+]);
72+match(stderr, error);
73+strictEqual(stdout, '');
74+strictEqual(code, 1);
75+strictEqual(signal, null);
76+}
77+});
78+});