karatelabs/karate · error · ParserException
'await' is a reserved word in a class static initialization…
Error message
'await' is a reserved word in a class static initialization block
What it means
Inside a class static initialization block, `await` is a reserved word and cannot be used as an identifier (the block is implicitly an async-like context). The Karate JS parser throws this when `await` appears in identifier position, except as a member name after `.` or `?.` (e.g. `x.await` is allowed). Rename the identifier.
Solutions
- Rename the identifier from `await` to something else (e.g. `awaitResult`, `aWait`).
- Access members via dot syntax (`obj.await`) which remains legal, instead of destructuring/shorthand using the bare word.
- Move the code out of the static block into a regular static method if the identifier cannot be renamed.
Example fix
// before
class C { static { let await = fetchCfg(); } }
// after
class C { static { let cfg = fetchCfg(); } } Defensive patterns
Strategy: validation
Validate before calling
// flag `await` used as a bare identifier inside static block sources
function awaitSafe(src) { return !/(?<![\w$.])await(?![\w$])(?!\s*:)/.test(src.replace(/\.await|\?\.await/g, '')); } Try / catch
try { karate.eval(blockSrc); } catch (e) { if (String(e).includes("'await' is a reserved word")) { /* rename identifier */ } } Prevention
- Never use reserved words (`await`, `yield`, `let`) as identifiers.
- When migrating code into class static blocks, rename legacy `await` variables.
- Configure linters to disallow reserved-word identifiers.
When it happens
Trigger: Parsing a class `static { ... }` block whose body uses `await` as a variable name or property shorthand (`{ await }`, `let await = ...`), detected by the static-block body walker with keepAwait member-access exemption.
Common situations: Code using `await` as a variable (legal in sloppy non-module scripts) being moved into a static block; minified/generated code that picked `await` as a name; upgrading class fields to static blocks during refactoring.
Related errors
- 'return' is not allowed in a class static initialization…
- 'break' may not cross a class static initialization block
- parser state: [ ]
- optional chain is not a valid assignment target
- unary expression cannot be the base of '**'; wrap it in…
AI-assisted analysis of karatelabs/karate@a22eb90246 (2026-09-12).
Data as JSON: /api/errors/408ac2233e406034.
Report an issue: GitHub.
Appendix: source
Thrown at karate-js/src/main/java/io/karatelabs/parser/JsParser.java:685
* check is on the token — skipping the positions where it is a property name
* rather than a reference.</li>
* </ul>
* {@code arguments} is equally illegal per spec but is not rejected here: telling a
* reference from the many legal {@code x.arguments} / {@code {arguments: …}} spellings
* costs more than the rule is worth.
*/
private void checkStaticBlockBody(Node node, int flags) {
boolean keepAwait = (flags & SB_AWAIT_OK) == 0 && !isPropertyNameHolder(node);
int last = node.size() - 1;
TokenType prev = null;
for (int i = 0; i <= last; i++) {
Node child = node.get(i);
if (child.isToken()) {
TokenType type = child.token.type;
// `x.await` / `x?.await` name a member, they do not reference one
if (keepAwait && type == IDENT && prev != DOT && prev != QUES_DOT
&& isIdentText(child.token, "await")) {
throw new ParserException("'await' is a reserved word in a class static initialization block");
}
prev = type;
continue;
}
prev = null;
int childFlags = flags;
switch (child.type) {
case RETURN_STMT -> {
if ((flags & SB_FN) == 0) {
throw new ParserException("'return' is not allowed in a class static initialization block");
}
}
case BREAK_STMT -> {
if ((flags & (SB_FN | SB_LOOP | SB_SWITCH)) == 0 && child.size() == 1) {
throw new ParserException("'break' may not cross a class static initialization block");
}
}
case CONTINUE_STMT -> {View on GitHub (pinned to a22eb90246)