evanw / evanw/esbuild

SyntaxError: 'super' keyword unexpected here

Open
#4,495 0 comments 0 reactions 0 assignees View on GitHub
Dominant language
Go
Stars
40.1k
Forks
1.3k
PR merge metrics
No merged PRs in 30d

Description

Hi @evanw ,
I was trying to upgrade a codebase which is using `esbuild` to produce compiled output.
After upgrading the `c12` package which also upgraded `exsolve`, esbuild produces wrong code for the `node10` target.

Here is an excerpt of `exsolve` to reproduce the issue on [esbuild try](https://esbuild.github.io/try/#YgAwLjI4LjEALS1idW5kbGUgLS1taW5pZnk9ZmFsc2UgLS1wbGF0Zm9ybT1ub2RlIGluZGV4Lm1qcyAtLW91dGZpbGU9ZGlzdC9pbmRleC5qcyAtLXRhcmdldD1ub2RlMTAAZQBpbmRleC5tanMAZnVuY3Rpb24gbWFrZU5vZGVFcnJvcldpdGhDb2RlKEJhc2UsIGtleSkgewoJCQljbGFzcyBOb2RlRXJyb3IgZXh0ZW5kcyBCYXNlIHsKCQkJCWNvZGUgPSBrZXk7CgkJCQljb25zdHJ1Y3RvciguLi5hcmdzKSB7CgkJCQkJYXNzZXJ0Lm9rKGFyZ3MubGVuZ3RoID09PSAwLCBgQ29kZTogJHtrZXl9OyBUaGUgcHJvdmlkZWQgYXJndW1lbnRzIGxlbmd0aCAoJHthcmdzLmxlbmd0aH0pIGRvZXMgbm90IG1hdGNoIHRoZSByZXF1aXJlZCBvbmVzICgke2V4cGVjdGVkTGVuZ3RofSkuYCk7CgkJCQkJc3VwZXIobWVzc2FnZSk7CgkJCQl9CgkJCQlnZXQgWyJjb25zdHJ1Y3RvciJdKCkgewoJCQkJCXJldHVybiBCYXNlOwoJCQkJfQoJCQkJZ2V0IFtrSXNOb2RlRXJyb3JdKCkgewoJCQkJCXJldHVybiB0cnVlOwoJCQkJfQoJCQkJdG9TdHJpbmcoKSB7CgkJCQkJcmV0dXJuIGAke3RoaXMubmFtZX0gWyR7a2V5fV06ICR7dGhpcy5tZXNzYWdlfWA7CgkJCQl9CgkJCX0KCQkJcmV0dXJuIE5vZGVFcnJvcjsKfQptYWtlTm9kZUVycm9yV2l0aENvZGUoRXJyb3IsIDApOw)

index.mjs

```javascript
function makeNodeErrorWithCode(Base, key) {
class NodeError extends Base {
code = key;
constructor(...args) {
assert.ok(args.length === 0, `Code: ${key}; The provided arguments length (${args.length}) does not match the required ones (${expectedLength}).`);
super(message);
}
get ["constructor"]() {
return Base;
}
get [kIsNodeError]() {
return true;
}
toString() {
return `${this.name} [${key}]: ${this.message}`;
}
}
return NodeError;
}
makeNodeErrorWithCode(Error, 0);
```


When you run `esbuild` with
```shell
npx esbuild --bundle --minify=false --platform=node index.mjs --outfile=dist/index.js --target=node10
```
it is transpiled to the following

dist/index.js

```javascript
var __defProp = Object.defineProperty;
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);

// index.mjs
function makeNodeErrorWithCode(Base, key) {
class NodeError extends Base {
get ["constructor"]() {
var __super = (...args) => {
super(...args);
__publicField(this, "code", key);
return this;
};
return Base;
}
constructor(...args2) {
assert.ok(args2.length === 0, `Code: ${key}; The provided arguments length (${args2.length}) does not match the required ones (${expectedLength}).`);
__super(message);
}
get [kIsNodeError]() {
return true;
}
toString() {
return `${this.name} [${key}]: ${this.message}`;
}
}
return NodeError;
}
makeNodeErrorWithCode(Error, 0);
```


Now when you try to run this with `node ./dist/index.js`, you get the following error:
```shell
super(...args);
^^^^^

SyntaxError: 'super' keyword unexpected here
```

It looks like this block
```javascript
var __super = (...args) => {
super(...args);
__publicField(this, "code", key);
return this;
};
```
is placed in the wrong location.
It should be placed into the `constructor` instead.

Contributor guide

No contributing guide indexed for this repository

Research direction

Reproduce the issue with the linked esbuild try case or with index.mjs and the node10 command, then inspect the generated dist/index.js. Trace the lowering of the class field and computed constructor getter, focusing on where the __super helper is emitted. Done means the generated node10 output keeps super inside a valid class constructor context and runs without the reported SyntaxError.

Written by the indexing model from the issue text.

Assessment

Tech stack
go, javascript
Domain
compilers
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Clearly specified
Newbie friendliness
55/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.