The abstract operation GetClassEnvironment takes no arguments. It finds the Environment Record that currently supplies the binding of the keyword `class` for a |ClassProperty|. It performs the following steps when called:
4 |
5 | 1. Let _env_ be GetThisEnvironment().
6 | 1. Let _exists_ be _env_.HasClassBinding().
7 | 1. If _exists_ is *true*, return _env_.
8 | 1. Return *undefined*.
9 |
10 |
11 |
--------------------------------------------------------------------------------
/spec/sec-makemethod-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
MakeMethod ( _F_, _homeObject_, _classObject_ )
3 |
The abstract operation MakeMethod takes arguments _F_ and _homeObject_, _homeObject_, and _classObject_. It configures _F_ as a method. It performs the following steps when called:
4 |
5 | 1. Assert: _F_ is an ECMAScript function object.
6 | 1. Assert: Type(_homeObject_) is Object.
7 | 1. Assert: Type(_classObject_) is either Object or Undefined.
8 | 1. Set _F_.[[HomeObject]] to _homeObject_.
9 | 1. Set _F_.[[InitialClassObject]] to _classObject_.
10 | 1. Return NormalCompletion(*undefined*).
11 |
12 |
--------------------------------------------------------------------------------
/spec/sec-static-semantics-static-semantics-assignmenttargettype-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 | ArrowFunction : ArrowParameters `=>` ConciseBody
6 |
7 | 1. If _symbol_ is not one of |NewTarget|, |SuperProperty|, |SuperCall|, |ClassProperty|, `super`, `class` or `this`, return *false*.
8 | 1. If |ArrowParameters| Contains _symbol_ is *true*, return *true*.
9 | 1. Return |ConciseBody| Contains _symbol_.
10 |
11 |
12 |
Normally, Contains does not look inside most function forms. However, Contains is used to detect `new.target`, `this`, and `super`, `super` and `class`-property usage within an |ArrowFunction|.
The abstract operation NewFunctionEnvironment takes arguments _F_ and _newTarget_. It performs the following steps when called:
4 |
5 | 1. Assert: _F_ is an ECMAScript function.
6 | 1. Assert: Type(_newTarget_) is Undefined or Object.
7 | 1. Let _env_ be a new function Environment Record containing no bindings.
8 | 1. Set _env_.[[FunctionObject]] to _F_.
9 | 1. If _F_.[[ThisMode]] is ~lexical~, set _env_.[[ThisBindingStatus]] to ~lexical~.
10 | 1. Else, set _env_.[[ThisBindingStatus]] to ~uninitialized~.
11 | 1. Let _home_ be _F_.[[HomeObject]].
12 | 1. Set _env_.[[HomeObject]] to _home_.
13 | 1. Let _classObject_ be _F_.[[InitialClassObject]].
14 | 1. Set _env_.[[InitialClassObject]] to _classObject_.
15 | 1. Set _env_.[[NewTarget]] to _newTarget_.
16 | 1. Set _env_.[[OuterEnv]] to _F_.[[Environment]].
17 | 1. Return _env_.
18 |
19 |
20 |
--------------------------------------------------------------------------------
/spec/sec-runtime-semantics-definemethod-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
Runtime Semantics: DefineMethod
3 |
With parameter _object_ and optional parameter _functionPrototype_parameters _functionPrototype_ and _classObject_.
4 | MethodDefinition : PropertyName `(` UniqueFormalParameters `)` `{` FunctionBody `}`
5 |
6 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
7 | 1. ReturnIfAbrupt(_propKey_).
8 | 1. Let _scope_ be the running execution context's LexicalEnvironment.
9 | 1. If _functionPrototype_ is present, then
10 | 1. Let _prototype_ be _functionPrototype_.
11 | 1. Else,
12 | 1. Let _prototype_ be %Function.prototype%.
13 | 1. Let _sourceText_ be the source text matched by |MethodDefinition|.
14 | 1. Let _closure_ be OrdinaryFunctionCreate(_prototype_, _sourceText_, |UniqueFormalParameters|, |FunctionBody|, ~non-lexical-this~, _scope_).
15 | 1. Perform MakeMethod(_closure_, _object_, _classObject_).
16 | 1. Return the Record { [[Key]]: _propKey_, [[Closure]]: _closure_ }.
17 |
18 |
--------------------------------------------------------------------------------
/spec/sec-async-function-definitions-PropertyDefinitionEvaluation-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
Runtime Semantics: PropertyDefinitionEvaluation
3 |
With parameters _object_ and _enumerable_, _enumerable_, and optional parameter _classObject_.
4 |
5 | AsyncMethod : `async` PropertyName `(` UniqueFormalParameters `)` `{` AsyncFunctionBody `}`
6 |
7 |
8 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
9 | 1. ReturnIfAbrupt(_propKey_).
10 | 1. Let _scope_ be the LexicalEnvironment of the running execution context.
11 | 1. Let _sourceText_ be the source text matched by |AsyncMethod|.
12 | 1. Let _closure_ be ! OrdinaryFunctionCreate(%AsyncFunction.prototype%, _sourceText_, |UniqueFormalParameters|, |AsyncFunctionBody|, ~non-lexical-this~, _scope_).
13 | 1. Perform ! MakeMethod(_closure_, _object_, _classObject_).
14 | 1. Perform ! SetFunctionName(_closure_, _propKey_).
15 | 1. Let _desc_ be the PropertyDescriptor { [[Value]]: _closure_, [[Writable]]: *true*, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
16 | 1. Return ? DefinePropertyOrThrow(_object_, _propKey_, _desc_).
17 |
18 |
--------------------------------------------------------------------------------
/spec/sec-async-arrow-function-definitions-static-semantics-Contains-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
Static Semantics: Contains
3 |
With parameter _symbol_.
4 |
5 | AsyncArrowFunction : `async` AsyncArrowBindingIdentifier `=>` AsyncConciseBody
6 |
7 |
8 | 1. If _symbol_ is not one of |NewTarget|, |SuperProperty|, |SuperCall|, |ClassProperty|, `super`, `class`, or `this`, return *false*.
9 | 1. Return |AsyncConciseBody| Contains _symbol_.
10 |
11 |
12 | AsyncArrowFunction : CoverCallExpressionAndAsyncArrowHead `=>` AsyncConciseBody
13 |
14 |
15 | 1. If _symbol_ is not one of |NewTarget|, |SuperProperty|, |SuperCall|, |ClassProperty|, `super`, `class`, or `this`, return *false*.
16 | 1. Let _head_ be CoveredAsyncArrowHead of |CoverCallExpressionAndAsyncArrowHead|.
17 | 1. If _head_ Contains _symbol_ is *true*, return *true*.
18 | 1. Return |AsyncConciseBody| Contains _symbol_.
19 |
20 | Normally, Contains does not look inside most function forms. However, Contains is used to detect `new.target`, `this`, and `super`, `super`, and `class`-property usage within an AsyncArrowFunction.
21 |
22 |
--------------------------------------------------------------------------------
/spec/sec-static-semantics-static-semantics-contains-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
With parameter _object_ and _enumerable_, _enumerable_, and optional parameter _classObject_.
4 |
5 | AsyncGeneratorMethod : `async` `*` PropertyName `(` UniqueFormalParameters `)` `{` AsyncGeneratorBody `}`
6 |
7 |
8 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
9 | 1. ReturnIfAbrupt(_propKey_).
10 | 1. Let _scope_ be the running execution context's LexicalEnvironment.
11 | 1. Let _sourceText_ be the source text matched by |AsyncGeneratorMethod|.
12 | 1. Let _closure_ be ! OrdinaryFunctionCreate(%AsyncGeneratorFunction.prototype%, _sourceText_, |UniqueFormalParameters|, |AsyncGeneratorBody|, ~non-lexical-this~, _scope_).
13 | 1. Perform ! MakeMethod(_closure_, _object_, _classObject_).
14 | 1. Perform ! SetFunctionName(_closure_, _propKey_).
15 | 1. Let _prototype_ be ! OrdinaryObjectCreate(%AsyncGeneratorFunction.prototype.prototype%).
16 | 1. Perform ! DefinePropertyOrThrow(_closure_, *"prototype"*, PropertyDescriptor { [[Value]]: _prototype_, [[Writable]]: *true*, [[Enumerable]]: *false*, [[Configurable]]: *false* }).
17 | 1. Let _desc_ be PropertyDescriptor { [[Value]]: _closure_, [[Writable]]: *true*, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
18 | 1. Return ? DefinePropertyOrThrow(_object_, _propKey_, _desc_).
19 |
20 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | BSD 3-Clause License
2 |
3 | Copyright (c) 2017, Ron Buckton, Ecma International
4 | All rights reserved.
5 |
6 | Redistribution and use in source and binary forms, with or without
7 | modification, are permitted provided that the following conditions are met:
8 |
9 | * Redistributions of source code must retain the above copyright notice, this
10 | list of conditions and the following disclaimer.
11 |
12 | * Redistributions in binary form must reproduce the above copyright notice,
13 | this list of conditions and the following disclaimer in the documentation
14 | and/or other materials provided with the distribution.
15 |
16 | * Neither the name of the copyright holder nor the names of its
17 | contributors may be used to endorse or promote products derived from
18 | this software without specific prior written permission.
19 |
20 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
23 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
24 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
26 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
27 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
28 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 |
--------------------------------------------------------------------------------
/spec/sec-left-hand-side-expressions-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
With parameters _object_ and _enumerable_, _enumerable_, and optional parameter _classObject_.
4 |
5 | GeneratorMethod : `*` PropertyName `(` UniqueFormalParameters `)` `{` GeneratorBody `}`
6 |
7 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
8 | 1. ReturnIfAbrupt(_propKey_).
9 | 1. Let _scope_ be the running execution context's LexicalEnvironment.
10 | 1. Let _sourceText_ be the source text matched by |GeneratorMethod|.
11 | 1. Let _closure_ be OrdinaryFunctionCreate(%GeneratorFunction.prototype%, _sourceText_, |UniqueFormalParameters|, |GeneratorBody|, ~non-lexical-this~, _scope_).
12 | 1. Perform MakeMethod(_closure_, _object_, _classObject_).
13 | 1. Perform SetFunctionName(_closure_, _propKey_).
14 | 1. Let _prototype_ be ! OrdinaryObjectCreate(%GeneratorFunction.prototype.prototype%).
15 | 1. Perform DefinePropertyOrThrow(_closure_, *"prototype"*, PropertyDescriptor { [[Value]]: _prototype_, [[Writable]]: *true*, [[Enumerable]]: *false*, [[Configurable]]: *false* }).
16 | 1. Let _desc_ be the PropertyDescriptor { [[Value]]: _closure_, [[Writable]]: *true*, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
17 | 1. Return ? DefinePropertyOrThrow(_object_, _propKey_, _desc_).
18 |
19 |
--------------------------------------------------------------------------------
/spec/sec-arrow-function-definitions-runtime-semantics-namedevaluation-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
Runtime Semantics: NamedEvaluation
3 |
With parameter _name_.
4 | ArrowFunction : ArrowParameters `=>` ConciseBody
5 |
6 | 1. Let _scope_ be the LexicalEnvironment of the running execution context.
7 | 1. Let _sourceText_ be the source text matched by |ArrowFunction|.
8 | 1. Let _parameters_ be CoveredFormalsList of |ArrowParameters|.
9 | 1. [id="step-arrowfunction-evaluation-functioncreate"] Let _closure_ be OrdinaryFunctionCreate(%Function.prototype%, _sourceText_, _parameters_, |ConciseBody|, ~lexical-this~, _scope_).
10 | 1. Perform SetFunctionName(_closure_, _name_).
11 | 1. Return _closure_.
12 |
13 |
14 |
An |ArrowFunction| does not define local bindings for `arguments`, `super`, `class`, `this`, or `new.target`. Any reference to `arguments`, `super`, `class`, `this`, or `new.target` within an |ArrowFunction| must resolve to a binding in a lexically enclosing environment. Typically this will be the Function Environment of an immediately enclosing function. Even though an |ArrowFunction| may contain references to `super`, the function object created in step is not made into a method by performing MakeMethod. An |ArrowFunction| that references `super` or `class` is always contained within a non-|ArrowFunction| and the necessary state to implement `super` or `class` is accessible via the _scope_ that is captured by the function object of the |ArrowFunction|.
6 |
7 | ClassProperty : `class` `[` Expression `]`
8 |
9 | 1. Let _env_ be GetClassEnvironment().
10 | 1. If _env_ is *undefined* throw a *TypeError* exception.
11 | 1. Let _classObject_ be ? _env_.GetClassBinding().
12 | 1. If _classObject_ is *undefined* throw a *TypeError* exception.
13 | 1. If the code matched by this |ClassProperty| is strict mode code, let _strict_ be *true*; else let _strict_ be *false*.
14 | 1. Return ? EvaluatePropertyAccessWithExpressionKey(_classObject_, |Expression|, _strict_).
15 |
16 |
17 | ClassProperty : `class` `.` IdentifierName
18 |
19 | 1. Let _env_ be GetClassEnvironment().
20 | 1. If _env_ is *undefined* throw a *TypeError* exception.
21 | 1. Let _classObject_ be ? _env_.GetClassBinding().
22 | 1. If _classObject_ is *undefined* throw a *TypeError* exception.
23 | 1. If the code matched by this |ClassProperty| is strict mode code, let _strict_ be *true*; else let _strict_ be *false*.
24 | 1. Return ? EvaluatePropertyAccessWithIdentifierKey(_classObject_, |IdentifierName|, _strict_).
25 |
26 |
27 | ClassProperty : `class` `.` PrivateIdentifier
28 |
29 | 1. Let _env_ be GetClassEnvironment().
30 | 1. If _env_ is *undefined* throw a *TypeError* exception.
31 | 1. Let _classObject_ be ? _env_.GetClassBinding().
32 | 1. If _classObject_ is *undefined* throw a *TypeError* exception.
33 | 1. Return ? MakePrivateReference(_classObject_, |PrivateIdentifier|).
34 |
35 |
36 |
--------------------------------------------------------------------------------
/spec/sec-function-definitions-static-semantics-early-errors-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
12 | If the source code matching |FormalParameters| is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
13 |
14 |
15 | If |BindingIdentifier| is present and the source code matching |BindingIdentifier| is strict mode code, it is a Syntax Error if the StringValue of |BindingIdentifier| is *"eval"* or *"arguments"*.
16 |
17 |
18 | It is a Syntax Error if ContainsUseStrict of |FunctionBody| is *true* and IsSimpleParameterList of |FormalParameters| is *false*.
19 |
20 |
21 | It is a Syntax Error if any element of the BoundNames of |FormalParameters| also occurs in the LexicallyDeclaredNames of |FunctionBody|.
22 |
23 |
24 | It is a Syntax Error if |FormalParameters| Contains |SuperProperty| is *true*.
25 |
26 |
27 | It is a Syntax Error if |FunctionBody| Contains |SuperProperty| is *true*.
28 |
29 |
30 | It is a Syntax Error if |FormalParameters| Contains |SuperCall| is *true*.
31 |
32 |
33 | It is a Syntax Error if |FunctionBody| Contains |SuperCall| is *true*.
34 |
35 |
36 | It is a Syntax Error if |FormalParameters| Contains |ClassProperty| is *true*.
37 |
38 |
39 | It is a Syntax Error if |FunctionBody| Contains |ClassProperty| is *true*.
40 |
6 | It is a Syntax Error if the LexicallyDeclaredNames of |ScriptBody| contains any duplicate entries.
7 |
8 |
9 | It is a Syntax Error if any element of the LexicallyDeclaredNames of |ScriptBody| also occurs in the VarDeclaredNames of |ScriptBody|.
10 |
11 |
12 | ScriptBody : StatementList
13 |
14 |
15 | It is a Syntax Error if |StatementList| Contains `super` unless the source code containing `super` is eval code that is being processed by a direct eval. Additional early error rules for `super` within direct eval are defined in .
16 |
17 |
18 | It is a Syntax Error if |StatementList| Contains |ClassProperty| unless the source code containing |ClassProperty| is eval code that is being processed by a direct eval. Additional early error rules for |ClassProperty| within direct eval are defined in .
19 |
20 |
21 | It is a Syntax Error if |StatementList| Contains |NewTarget| unless the source code containing |NewTarget| is eval code that is being processed by a direct eval. Additional early error rules for |NewTarget| in direct eval are defined in .
22 |
23 |
24 | It is a Syntax Error if ContainsDuplicateLabels of |StatementList| with argument « » is *true*.
25 |
26 |
27 | It is a Syntax Error if ContainsUndefinedBreakTarget of |StatementList| with argument « » is *true*.
28 |
29 |
30 | It is a Syntax Error if ContainsUndefinedContinueTarget of |StatementList| with arguments « » and « » is *true*.
31 |
It is a Syntax Error if ContainsUseStrict of |AsyncFunctionBody| is *true* and IsSimpleParameterList of |FormalParameters| is *false*.
14 |
It is a Syntax Error if |FormalParameters| Contains |AwaitExpression| is *true*.
15 |
If the source code matching |FormalParameters| is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
16 |
If |BindingIdentifier| is present and the source code matching |BindingIdentifier| is strict mode code, it is a Syntax Error if the StringValue of |BindingIdentifier| is *"eval"* or *"arguments"*.
17 |
It is a Syntax Error if any element of the BoundNames of |FormalParameters| also occurs in the LexicallyDeclaredNames of |AsyncFunctionBody|.
18 |
It is a Syntax Error if |FormalParameters| Contains |SuperProperty| is *true*.
19 |
It is a Syntax Error if |AsyncFunctionBody| Contains |SuperProperty| is *true*.
20 |
It is a Syntax Error if |FormalParameters| Contains |SuperCall| is *true*.
21 |
It is a Syntax Error if |AsyncFunctionBody| Contains |SuperCall| is *true*.
22 |
It is a Syntax Error if |FormalParameters| Contains |ClassProperty| is *true*.
23 |
It is a Syntax Error if |AsyncFunctionBody| Contains |ClassProperty| is *true*.
6 | It is a Syntax Error if the LexicallyDeclaredNames of |ModuleItemList| contains any duplicate entries.
7 |
8 |
9 | It is a Syntax Error if any element of the LexicallyDeclaredNames of |ModuleItemList| also occurs in the VarDeclaredNames of |ModuleItemList|.
10 |
11 |
12 | It is a Syntax Error if the ExportedNames of |ModuleItemList| contains any duplicate entries.
13 |
14 |
15 | It is a Syntax Error if any element of the ExportedBindings of |ModuleItemList| does not also occur in either the VarDeclaredNames of |ModuleItemList|, or the LexicallyDeclaredNames of |ModuleItemList|.
16 |
17 |
18 | It is a Syntax Error if |ModuleItemList| Contains `super`.
19 |
20 |
21 | It is a Syntax Error if |ModuleItemList| Contains |ClassProperty|.
22 |
23 |
24 | It is a Syntax Error if |ModuleItemList| Contains |NewTarget|.
25 |
26 |
27 | It is a Syntax Error if ContainsDuplicateLabels of |ModuleItemList| with argument « » is *true*.
28 |
29 |
30 | It is a Syntax Error if ContainsUndefinedBreakTarget of |ModuleItemList| with argument « » is *true*.
31 |
32 |
33 | It is a Syntax Error if ContainsUndefinedContinueTarget of |ModuleItemList| with arguments « » and « » is *true*.
34 |
35 |
36 |
37 |
The duplicate ExportedNames rule implies that multiple `export default` |ExportDeclaration| items within a |ModuleBody| is a Syntax Error. Additional error conditions relating to conflicting or duplicate declarations are checked during module linking prior to evaluation of a |Module|. If any such errors are detected the |Module| is not evaluated.
If the source code matching |FormalParameters| is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
12 |
If |BindingIdentifier| is present and the source code matching |BindingIdentifier| is strict mode code, it is a Syntax Error if the StringValue of |BindingIdentifier| is *"eval"* or *"arguments"*.
13 |
It is a Syntax Error if ContainsUseStrict of |AsyncGeneratorBody| is *true* and IsSimpleParameterList of |FormalParameters| is *false*.
14 |
It is a Syntax Error if any element of the BoundNames of |FormalParameters| also occurs in the LexicallyDeclaredNames of |AsyncGeneratorBody|.
15 |
It is a Syntax Error if |FormalParameters| Contains |YieldExpression| is *true*.
16 |
It is a Syntax Error if |FormalParameters| Contains |AwaitExpression| is *true*.
17 |
It is a Syntax Error if |FormalParameters| Contains |SuperProperty| is *true*.
18 |
It is a Syntax Error if |AsyncGeneratorBody| Contains |SuperProperty| is *true*.
19 |
It is a Syntax Error if |FormalParameters| Contains |SuperCall| is *true*.
20 |
It is a Syntax Error if |AsyncGeneratorBody| Contains |SuperCall| is *true*.
21 |
It is a Syntax Error if |FormalParameters| Contains |ClassProperty| is *true*.
22 |
It is a Syntax Error if |AsyncGeneratorBody| Contains |ClassProperty| is *true*.
12 | If the source code matching |FormalParameters| is strict mode code, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
13 |
14 |
15 | If |BindingIdentifier| is present and the source code matching |BindingIdentifier| is strict mode code, it is a Syntax Error if the StringValue of |BindingIdentifier| is *"eval"* or *"arguments"*.
16 |
17 |
18 | It is a Syntax Error if ContainsUseStrict of |GeneratorBody| is *true* and IsSimpleParameterList of |FormalParameters| is *false*.
19 |
20 |
21 | It is a Syntax Error if any element of the BoundNames of |FormalParameters| also occurs in the LexicallyDeclaredNames of |GeneratorBody|.
22 |
23 |
24 | It is a Syntax Error if |FormalParameters| Contains |YieldExpression| is *true*.
25 |
26 |
27 | It is a Syntax Error if |FormalParameters| Contains |SuperProperty| is *true*.
28 |
29 |
30 | It is a Syntax Error if |GeneratorBody| Contains |SuperProperty| is *true*.
31 |
32 |
33 | It is a Syntax Error if |FormalParameters| Contains |SuperCall| is *true*.
34 |
35 |
36 | It is a Syntax Error if |GeneratorBody| Contains |SuperCall| is *true*.
37 |
38 |
39 | It is a Syntax Error if |FormalParameters| Contains |ClassProperty| is *true*.
40 |
41 |
42 | It is a Syntax Error if |GeneratorBody| Contains |ClassProperty| is *true*.
43 |
With parameters _object_ and _enumerable_, _enumerable_, and optional parameter _classObject_.
4 |
5 | MethodDefinition : PropertyName `(` UniqueFormalParameters `)` `{` FunctionBody `}`
6 |
7 | 1. Let _methodDef_ be ? DefineMethod of |MethodDefinition| with argument _object_arguments _object_, *undefined*, and _classObject_.
8 | 1. Perform SetFunctionName(_methodDef_.[[Closure]], _methodDef_.[[Key]]).
9 | 1. Let _desc_ be the PropertyDescriptor { [[Value]]: _methodDef_.[[Closure]], [[Writable]]: *true*, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
10 | 1. Return ? DefinePropertyOrThrow(_object_, _methodDef_.[[Key]], _desc_).
11 |
12 | MethodDefinition : `get` PropertyName `(` `)` `{` FunctionBody `}`
13 |
14 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
15 | 1. ReturnIfAbrupt(_propKey_).
16 | 1. Let _scope_ be the running execution context's LexicalEnvironment.
17 | 1. Let _sourceText_ be the source text matched by |MethodDefinition|.
18 | 1. Let _formalParameterList_ be an instance of the production FormalParameters : [empty].
19 | 1. Let _closure_ be OrdinaryFunctionCreate(%Function.prototype%, _sourceText_, _formalParameterList_, |FunctionBody|, ~non-lexical-this~, _scope_).
20 | 1. Perform MakeMethod(_closure_, _object_, _classObject_).
21 | 1. Perform SetFunctionName(_closure_, _propKey_, *"get"*).
22 | 1. Let _desc_ be the PropertyDescriptor { [[Get]]: _closure_, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
23 | 1. Return ? DefinePropertyOrThrow(_object_, _propKey_, _desc_).
24 |
25 | MethodDefinition : `set` PropertyName `(` PropertySetParameterList `)` `{` FunctionBody `}`
26 |
27 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
28 | 1. ReturnIfAbrupt(_propKey_).
29 | 1. Let _scope_ be the running execution context's LexicalEnvironment.
30 | 1. Let _sourceText_ be the source text matched by |MethodDefinition|.
31 | 1. Let _closure_ be OrdinaryFunctionCreate(%Function.prototype%, _sourceText_, |PropertySetParameterList|, |FunctionBody|, ~non-lexical-this~, _scope_).
32 | 1. Perform MakeMethod(_closure_, _object_, _classObject_).
33 | 1. Perform SetFunctionName(_closure_, _propKey_, *"set"*).
34 | 1. Let _desc_ be the PropertyDescriptor { [[Set]]: _closure_, [[Enumerable]]: _enumerable_, [[Configurable]]: *true* }.
35 | 1. Return ? DefinePropertyOrThrow(_object_, _propKey_, _desc_).
36 |
37 |
38 |
--------------------------------------------------------------------------------
/spec/sec-object-initializer-runtime-semantics-propertydefinitionevaluation-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
Runtime Semantics: PropertyDefinitionEvaluation
3 |
With parameters _object_ and _enumerable_, _enumerable_, and optional parameter _classObject_.
4 |
5 | PropertyDefinitionList : PropertyDefinitionList `,` PropertyDefinition
6 |
7 | 1. Assert: _classObject_ is not present or Type(_classObject_) is Undefined.
8 | 1. Perform ? PropertyDefinitionEvaluation of |PropertyDefinitionList| with arguments _object_ and _enumerable_.
9 | 1. Return the result of performing PropertyDefinitionEvaluation of |PropertyDefinition| with arguments _object_ and _enumerable_.
10 |
11 | PropertyDefinition : `...` AssignmentExpression
12 |
13 | 1. Assert: _classObject_ is not present or Type(_classObject_) is Undefined.
14 | 1. Let _exprValue_ be the result of evaluating |AssignmentExpression|.
15 | 1. Let _fromValue_ be ? GetValue(_exprValue_).
16 | 1. Let _excludedNames_ be a new empty List.
17 | 1. Return ? CopyDataProperties(_object_, _fromValue_, _excludedNames_).
18 |
19 | PropertyDefinition : IdentifierReference
20 |
21 | 1. Assert: _classObject_ is not present or Type(_classObject_) is Undefined.
22 | 1. Let _propName_ be StringValue of |IdentifierReference|.
23 | 1. Let _exprValue_ be the result of evaluating |IdentifierReference|.
24 | 1. Let _propValue_ be ? GetValue(_exprValue_).
25 | 1. Assert: _enumerable_ is *true*.
26 | 1. Assert: _object_ is an ordinary, extensible object with no non-configurable properties.
27 | 1. Return ! CreateDataPropertyOrThrow(_object_, _propName_, _propValue_).
28 |
29 | PropertyDefinition : PropertyName `:` AssignmentExpression
30 |
31 | 1. Assert: _classObject_ is not present or Type(_classObject_) is Undefined.
32 | 1. Let _propKey_ be the result of evaluating |PropertyName|.
33 | 1. ReturnIfAbrupt(_propKey_).
34 | 1. If IsAnonymousFunctionDefinition(|AssignmentExpression|) is *true*, then
35 | 1. Let _propValue_ be NamedEvaluation of |AssignmentExpression| with argument _propKey_.
36 | 1. Else,
37 | 1. Let _exprValueRef_ be the result of evaluating |AssignmentExpression|.
38 | 1. Let _propValue_ be ? GetValue(_exprValueRef_).
39 | 1. Assert: _enumerable_ is *true*.
40 | 1. Assert: _object_ is an ordinary, extensible object with no non-configurable properties.
41 | 1. Return ! CreateDataPropertyOrThrow(_object_, _propKey_, _propValue_).
42 |
43 |
44 |
An alternative semantics for this production is given in .
A potential tail position call that is immediately followed by return GetValue of the call result is also a possible tail position call. Function calls cannot return reference values, so such a GetValue operation will always return the same value as the actual function call result.
4 | ClassTail : ClassHeritage? `{` ClassBody? `}`
5 |
6 | 1. Let _env_ be the LexicalEnvironment of the running execution context.
7 | 1. Let _classScope_ be NewDeclarativeEnvironment(_env_).
8 | 1. If _classBinding_ is not *undefined*, then
9 | 1. Perform _classScope_.CreateImmutableBinding(_classBinding_, *true*).
10 | 1. If |ClassHeritage_opt| is not present, then
11 | 1. Let _protoParent_ be %Object.prototype%.
12 | 1. Let _constructorParent_ be %Function.prototype%.
13 | 1. Else,
14 | 1. Set the running execution context's LexicalEnvironment to _classScope_.
15 | 1. Let _superclassRef_ be the result of evaluating |ClassHeritage|.
16 | 1. Set the running execution context's LexicalEnvironment to _env_.
17 | 1. Let _superclass_ be ? GetValue(_superclassRef_).
18 | 1. If _superclass_ is *null*, then
19 | 1. Let _protoParent_ be *null*.
20 | 1. Let _constructorParent_ be %Function.prototype%.
21 | 1. Else if IsConstructor(_superclass_) is *false*, throw a *TypeError* exception.
22 | 1. Else,
23 | 1. Let _protoParent_ be ? Get(_superclass_, *"prototype"*).
24 | 1. If Type(_protoParent_) is neither Object nor Null, throw a *TypeError* exception.
25 | 1. Let _constructorParent_ be _superclass_.
26 | 1. Let _proto_ be ! OrdinaryObjectCreate(_protoParent_).
27 | 1. If |ClassBody_opt| is not present, let _constructor_ be ~empty~.
28 | 1. Else, let _constructor_ be ConstructorMethod of |ClassBody|.
29 | 1. If _constructor_ is ~empty~, then
30 | 1. If |ClassHeritage_opt| is present, then
31 | 1. Set _constructor_ to the result of parsing the source text
32 |
constructor(...args) { super(...args); }
33 | using the syntactic grammar with the goal symbol |MethodDefinition[~Yield, ~Await]|.
34 | 1. Else,
35 | 1. Set _constructor_ to the result of parsing the source text
36 |
constructor() {}
37 | using the syntactic grammar with the goal symbol |MethodDefinition[~Yield, ~Await]|.
38 | 1. Set the running execution context's LexicalEnvironment to _classScope_.
39 | 1. Let _constructorInfo_ be ! DefineMethod of _constructor_ with arguments _proto_ and _constructorParent_.
40 | 1. Let _F_ be _constructorInfo_.[[Closure]].
41 | 1. Perform SetFunctionName(_F_, _className_).
42 | 1. Perform MakeConstructor(_F_, *false*, _proto_).
43 | 1. If |ClassHeritage_opt| is present, set _F_.[[ConstructorKind]] to ~derived~.
44 | 1. Set _F_.[[InitialClassObject]] to _F_.
45 | 1. Perform MakeClassConstructor(_F_).
46 | 1. Perform CreateMethodProperty(_proto_, *"constructor"*, _F_).
47 | 1. If |ClassBody_opt| is not present, let _methods_ be a new empty List.
48 | 1. Else, let _methods_ be NonConstructorMethodDefinitions of |ClassBody|.
49 | 1. For each |ClassElement| _m_ of _methods_, do
50 | 1. If IsStatic of _m_ is *false*, then
51 | 1. Let _status_ be PropertyDefinitionEvaluation of _m_ with arguments _proto_ and *false*, *false*, and _F_.
52 | 1. Else,
53 | 1. Let _status_ be PropertyDefinitionEvaluation of _m_ with arguments _F_ and *false*, *false*, and _F_.
54 | 1. If _status_ is an abrupt completion, then
55 | 1. Set the running execution context's LexicalEnvironment to _env_.
56 | 1. Return Completion(_status_).
57 | 1. Set the running execution context's LexicalEnvironment to _env_.
58 | 1. If _classBinding_ is not *undefined*, then
59 | 1. Perform _classScope_.InitializeBinding(_classBinding_, _F_).
60 | 1. Return _F_.
61 |
62 |
63 |
--------------------------------------------------------------------------------
/spec/sec-performeval-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
The abstract operation PerformEval takes arguments _x_, _callerRealm_, _strictCaller_, and _direct_. It performs the following steps when called:
4 |
5 | 1. Assert: If _direct_ is *false*, then _strictCaller_ is also *false*.
6 | 1. If Type(_x_) is not String, return _x_.
7 | 1. Let _evalRealm_ be the current Realm Record.
8 | 1. Perform ? HostEnsureCanCompileStrings(_callerRealm_, _evalRealm_).
9 | 1. Let _inFunction_ be *false*.
10 | 1. Let _inMethod_ be *false*.
11 | 1. Let _inDerivedConstructor_ be *false*.
12 | 1. If _direct_ is *true*, then
13 | 1. Let _thisEnvRec_ be ! GetThisEnvironment().
14 | 1. If _thisEnvRec_ is a function Environment Record, then
15 | 1. Let _F_ be _thisEnvRec_.[[FunctionObject]].
16 | 1. Set _inFunction_ to *true*.
17 | 1. Set _inMethod_ to _thisEnvRec_.HasSuperBinding().
18 | 1. If _F_.[[ConstructorKind]] is ~derived~, set _inDerivedConstructor_ to *true*.
19 | 1. Perform the following substeps in an implementation-defined order, possibly interleaving parsing and error detection:
20 | 1. Let _script_ be the ECMAScript code that is the result of parsing ! StringToCodePoints(_x_), for the goal symbol |Script|. If the parse fails, throw a *SyntaxError* exception. If any early errors are detected, throw a *SyntaxError* exception (but see also clause ).
21 | 1. If _script_ Contains |ScriptBody| is *false*, return *undefined*.
22 | 1. Let _body_ be the |ScriptBody| of _script_.
23 | 1. If _inFunction_ is *false*, and _body_ Contains |NewTarget|, throw a *SyntaxError* exception.
24 | 1. If _inMethod_ is *false*, and _body_ Contains |SuperProperty|, throw a *SyntaxError* exception.
25 | 1. If _inMethod_ is *false*, and _body_ Contains |ClassProperty|, throw a *SyntaxError* exception.
26 | 1. If _inDerivedConstructor_ is *false*, and _body_ Contains |SuperCall|, throw a *SyntaxError* exception.
27 | 1. If _strictCaller_ is *true*, let _strictEval_ be *true*.
28 | 1. Else, let _strictEval_ be IsStrict of _script_.
29 | 1. Let _runningContext_ be the running execution context.
30 | 1. NOTE: If _direct_ is *true*, _runningContext_ will be the execution context that performed the direct eval. If _direct_ is *false*, _runningContext_ will be the execution context for the invocation of the `eval` function.
31 | 1. If _direct_ is *true*, then
32 | 1. Let _lexEnv_ be NewDeclarativeEnvironment(_runningContext_'s LexicalEnvironment).
33 | 1. Let _varEnv_ be _runningContext_'s VariableEnvironment.
34 | 1. Else,
35 | 1. Let _lexEnv_ be NewDeclarativeEnvironment(_evalRealm_.[[GlobalEnv]]).
36 | 1. Let _varEnv_ be _evalRealm_.[[GlobalEnv]].
37 | 1. If _strictEval_ is *true*, set _varEnv_ to _lexEnv_.
38 | 1. If _runningContext_ is not already suspended, suspend _runningContext_.
39 | 1. Let _evalContext_ be a new ECMAScript code execution context.
40 | 1. Set _evalContext_'s Function to *null*.
41 | 1. Set _evalContext_'s Realm to _evalRealm_.
42 | 1. Set _evalContext_'s ScriptOrModule to _runningContext_'s ScriptOrModule.
43 | 1. Set _evalContext_'s VariableEnvironment to _varEnv_.
44 | 1. Set _evalContext_'s LexicalEnvironment to _lexEnv_.
45 | 1. Push _evalContext_ onto the execution context stack; _evalContext_ is now the running execution context.
46 | 1. Let _result_ be EvalDeclarationInstantiation(_body_, _varEnv_, _lexEnv_, _strictEval_).
47 | 1. If _result_.[[Type]] is ~normal~, then
48 | 1. Set _result_ to the result of evaluating _body_.
49 | 1. If _result_.[[Type]] is ~normal~ and _result_.[[Value]] is ~empty~, then
50 | 1. Set _result_ to NormalCompletion(*undefined*).
51 | 1. Suspend _evalContext_ and remove it from the execution context stack.
52 | 1. Resume the context that is now on the top of the execution context stack as the running execution context.
53 | 1. Return Completion(_result_).
54 |
55 |
56 |
The eval code cannot instantiate variable or function bindings in the variable environment of the calling context that invoked the eval if the calling context is evaluating formal parameter initializers or if either the code of the calling context or the eval code is strict mode code. Instead such bindings are instantiated in a new VariableEnvironment that is only accessible to the eval code. Bindings introduced by `let`, `const`, or `class` declarations are always instantiated in a new LexicalEnvironment.
The Environment Record abstract class includes the abstract specification methods defined in . These abstract methods have distinct concrete algorithms for each of the concrete subclasses.
5 |
6 |
7 |
8 |
9 |
10 | Method
11 |
12 |
13 | Purpose
14 |
15 |
16 |
17 |
18 | HasBinding(N)
19 |
20 |
21 | Determine if an Environment Record has a binding for the String value _N_. Return *true* if it does and *false* if it does not.
22 |
23 |
24 |
25 |
26 | CreateMutableBinding(N, D)
27 |
28 |
29 | Create a new but uninitialized mutable binding in an Environment Record. The String value _N_ is the text of the bound name. If the Boolean argument _D_ is *true* the binding may be subsequently deleted.
30 |
31 |
32 |
33 |
34 | CreateImmutableBinding(N, S)
35 |
36 |
37 | Create a new but uninitialized immutable binding in an Environment Record. The String value _N_ is the text of the bound name. If _S_ is *true* then attempts to set it after it has been initialized will always throw an exception, regardless of the strict mode setting of operations that reference that binding.
38 |
39 |
40 |
41 |
42 | InitializeBinding(N, V)
43 |
44 |
45 | Set the value of an already existing but uninitialized binding in an Environment Record. The String value _N_ is the text of the bound name. _V_ is the value for the binding and is a value of any ECMAScript language type.
46 |
47 |
48 |
49 |
50 | SetMutableBinding(N, V, S)
51 |
52 |
53 | Set the value of an already existing mutable binding in an Environment Record. The String value _N_ is the text of the bound name. _V_ is the value for the binding and may be a value of any ECMAScript language type. _S_ is a Boolean flag. If _S_ is *true* and the binding cannot be set throw a *TypeError* exception.
54 |
55 |
56 |
57 |
58 | GetBindingValue(N, S)
59 |
60 |
61 | Returns the value of an already existing binding from an Environment Record. The String value _N_ is the text of the bound name. _S_ is used to identify references originating in strict mode code or that otherwise require strict mode reference semantics. If _S_ is *true* and the binding does not exist throw a *ReferenceError* exception. If the binding exists but is uninitialized a *ReferenceError* is thrown, regardless of the value of _S_.
62 |
63 |
64 |
65 |
66 | DeleteBinding(N)
67 |
68 |
69 | Delete a binding from an Environment Record. The String value _N_ is the text of the bound name. If a binding for _N_ exists, remove the binding and return *true*. If the binding exists but cannot be removed return *false*. If the binding does not exist return *true*.
70 |
71 |
72 |
73 |
74 | HasThisBinding()
75 |
76 |
77 | Determine if an Environment Record establishes a `this` binding. Return *true* if it does and *false* if it does not.
78 |
79 |
80 |
81 |
82 | HasSuperBinding()
83 |
84 |
85 | Determine if an Environment Record establishes a `super` method binding. Return *true* if it does and *false* if it does not.
86 |
87 |
88 |
89 |
90 | HasClassBinding()
91 |
92 |
93 | Determine if an Environment Record establishes a `class` binding. Return *true* if it does and *false* if it does not.
94 |
95 |
96 |
97 |
98 | WithBaseObject()
99 |
100 |
101 | If this Environment Record is associated with a `with` statement, return the with object. Otherwise, return *undefined*.
102 |
ECMAScript function objects encapsulate parameterized ECMAScript code closed over a lexical environment and support the dynamic evaluation of that code. An ECMAScript function object is an ordinary object and has the same internal slots and the same internal methods as other ordinary objects. The code of an ECMAScript function object may be either strict mode code () or non-strict code. An ECMAScript function object whose code is strict mode code is called a strict function. One whose code is not strict mode code is called a non-strict function.
4 |
In addition to [[Extensible]] and [[Prototype]], ECMAScript function objects also have the internal slots listed in .
5 |
6 |
7 |
8 |
9 |
10 | Internal Slot
11 |
12 |
13 | Type
14 |
15 |
16 | Description
17 |
18 |
19 |
20 |
21 | [[Environment]]
22 |
23 |
24 | Environment Record
25 |
26 |
27 | The Environment Record that the function was closed over. Used as the outer environment when evaluating the code of the function.
28 |
29 |
30 |
31 |
32 | [[FormalParameters]]
33 |
34 |
35 | Parse Node
36 |
37 |
38 | The root parse node of the source text that defines the function's formal parameter list.
39 |
40 |
41 |
42 |
43 | [[ECMAScriptCode]]
44 |
45 |
46 | Parse Node
47 |
48 |
49 | The root parse node of the source text that defines the function's body.
50 |
51 |
52 |
53 |
54 | [[ConstructorKind]]
55 |
56 |
57 | ~base~ | ~derived~
58 |
59 |
60 | Whether or not the function is a derived class constructor.
61 |
62 |
63 |
64 |
65 | [[Realm]]
66 |
67 |
68 | Realm Record
69 |
70 |
71 | The realm in which the function was created and which provides any intrinsic objects that are accessed when evaluating the function.
72 |
73 |
74 |
75 |
76 | [[ScriptOrModule]]
77 |
78 |
79 | Script Record or Module Record
80 |
81 |
82 | The script or module in which the function was created.
83 |
84 |
85 |
86 |
87 | [[ThisMode]]
88 |
89 |
90 | ~lexical~ | ~strict~ | ~global~
91 |
92 |
93 | Defines how `this` references are interpreted within the formal parameters and code body of the function. ~lexical~ means that `this` refers to the *this* value of a lexically enclosing function. ~strict~ means that the *this* value is used exactly as provided by an invocation of the function. ~global~ means that a *this* value of *undefined* or *null* is interpreted as a reference to the global object, and any other *this* value is first passed to ToObject.
94 |
95 |
96 |
97 |
98 | [[Strict]]
99 |
100 |
101 | Boolean
102 |
103 |
104 | *true* if this is a strict function, *false* if this is a non-strict function.
105 |
106 |
107 |
108 |
109 | [[HomeObject]]
110 |
111 |
112 | Object
113 |
114 |
115 | If the function uses `super`, this is the object whose [[GetPrototypeOf]] provides the object where `super` property lookups begin.
116 |
117 |
118 |
119 |
120 | [[InitialClassObject]]
121 |
122 |
123 | Object | *undefined*
124 |
125 |
126 | If the function has `class` property access, this is the function object where `class` property lookups begin.
127 |
128 |
129 |
130 |
131 | [[SourceText]]
132 |
133 |
134 | sequence of Unicode code points
135 |
136 |
137 | The source text that defines the function.
138 |
139 |
140 |
141 |
142 | [[IsClassConstructor]]
143 |
144 |
145 | Boolean
146 |
147 |
148 | Indicates whether the function is a class constructor. (If *true*, invoking the function's [[Call]] will immediately throw a *TypeError* exception.)
149 |
A function Environment Record is a declarative Environment Record that is used to represent the top-level scope of a function and, if the function is not an |ArrowFunction|, provides a `this` binding. If a function is not an |ArrowFunction| function and references `super`, its function Environment Record also contains the state that is used to perform `super` method invocations from within the function. If a function is not an |ArrowFunction| function and references `class`, its function Environment Record also contains the state that is used to perform `class` property acccess from within the function.
4 |
Function Environment Records have the additional state fields listed in .
5 |
6 |
7 |
8 |
9 |
10 | Field Name
11 |
12 |
13 | Value
14 |
15 |
16 | Meaning
17 |
18 |
19 |
20 |
21 | [[ThisValue]]
22 |
23 |
24 | Any
25 |
26 |
27 | This is the *this* value used for this invocation of the function.
28 |
38 | If the value is ~lexical~, this is an |ArrowFunction| and does not have a local *this* value.
39 |
40 |
41 |
42 |
43 | [[FunctionObject]]
44 |
45 |
46 | Object
47 |
48 |
49 | The function object whose invocation caused this Environment Record to be created.
50 |
51 |
52 |
53 |
54 | [[HomeObject]]
55 |
56 |
57 | Object | *undefined*
58 |
59 |
60 | If the associated function has `super` property accesses and is not an |ArrowFunction|, [[HomeObject]] is the object that the function is bound to as a method. The default value for [[HomeObject]] is *undefined*.
61 |
62 |
63 |
64 |
65 | [[InitialClassObject]]
66 |
67 |
68 | Object | *undefined*
69 |
70 |
71 | If the associated function has `class` property access and is not an |ArrowFunction|, [[InitialClassObject]] is the class constructor function object that the function was initially bound to as a method. The default value for [[InitialClassObject]] is *undefined*.
72 |
73 |
74 |
75 |
76 | [[NewTarget]]
77 |
78 |
79 | Object | *undefined*
80 |
81 |
82 | If this Environment Record was created by the [[Construct]] internal method, [[NewTarget]] is the value of the [[Construct]] _newTarget_ parameter. Otherwise, its value is *undefined*.
83 |
84 |
85 |
86 |
87 |
88 |
Function Environment Records support all of the declarative Environment Record methods listed in and share the same specifications for all of those methods except for HasThisBinding and HasSuperBinding, HasSuperBinding, and HasClassBinding. In addition, function Environment Records support the methods listed in :
89 |
90 |
91 |
92 |
93 |
94 | Method
95 |
96 |
97 | Purpose
98 |
99 |
100 |
101 |
102 | BindThisValue(V)
103 |
104 |
105 | Set the [[ThisValue]] and record that it has been initialized.
106 |
107 |
108 |
109 |
110 | GetThisBinding()
111 |
112 |
113 | Return the value of this Environment Record's `this` binding. Throws a *ReferenceError* if the `this` binding has not been initialized.
114 |
115 |
116 |
117 |
118 | GetSuperBase()
119 |
120 |
121 | Return the object that is the base for `super` property accesses bound in this Environment Record. The object is derived from this Environment Record's [[HomeObject]] field. The value *undefined* indicates that `super` property accesses will produce runtime errors.
122 |
123 |
124 |
125 |
126 | GetClassBinding()
127 |
128 |
129 | Return the object that is the base for `class` property accesses bound in this Environment Record. The object is derived from this Environment Record's [[InitialClassObject]] field. The value *undefined* indicates that `class` property accesses will produce runtime errors.
130 |
131 |
132 |
133 |
134 |
135 |
The behaviour of the additional concrete specification methods for function Environment Records is defined by the following algorithms:
136 |
137 |
138 |
HasClassBinding ( )
139 |
140 | 1. Let _envRec_ be the function Environment Record for which the method was invoked.
141 | 1. If _envRec_.[[ThisBindingStatus]] is ~lexical~, return *false*.
142 | 1. If _envRec_.[[InitialClassObject]] has the value *undefined*, return *false*; otherwise, return *true*.
143 |
144 |
145 |
146 |
147 |
GetClassBinding ( )
148 |
149 | 1. Let _envRec_ be the function Environment Record for which the method was invoked.
150 | 1. Let _classObject_ be _envRec_.[[InitialClassObject]].
151 | 1. If _classObject_ has the value *undefined*, return *undefined*.
152 | 1. Assert: Type(_classObject_) is Object.
153 | 1. Return ? _classObject_.
154 |
155 |
156 |
157 |
--------------------------------------------------------------------------------
/spec/sec-createdynamicfunction-patch.html:
--------------------------------------------------------------------------------
1 |
2 |
The abstract operation CreateDynamicFunction takes arguments _constructor_ (a constructor), _newTarget_ (a constructor), _kind_ (either ~normal~, ~generator~, ~async~, or ~asyncGenerator~), and _args_ (a List of ECMAScript language values). _constructor_ is the constructor function that is performing this action. _newTarget_ is the constructor that `new` was initially applied to. _args_ is the argument values that were passed to _constructor_. It performs the following steps when called:
4 |
5 | 1. Assert: The execution context stack has at least two elements.
6 | 1. Let _callerContext_ be the second to top element of the execution context stack.
7 | 1. Let _callerRealm_ be _callerContext_'s Realm.
8 | 1. Let _calleeRealm_ be the current Realm Record.
9 | 1. Perform ? HostEnsureCanCompileStrings(_callerRealm_, _calleeRealm_).
10 | 1. If _newTarget_ is *undefined*, set _newTarget_ to _constructor_.
11 | 1. If _kind_ is ~normal~, then
12 | 1. Let _goal_ be the grammar symbol |FunctionBody[~Yield, ~Await]|.
13 | 1. Let _parameterGoal_ be the grammar symbol |FormalParameters[~Yield, ~Await]|.
14 | 1. Let _fallbackProto_ be *"%Function.prototype%"*.
15 | 1. Else if _kind_ is ~generator~, then
16 | 1. Let _goal_ be the grammar symbol |GeneratorBody|.
17 | 1. Let _parameterGoal_ be the grammar symbol |FormalParameters[+Yield, ~Await]|.
18 | 1. Let _fallbackProto_ be *"%GeneratorFunction.prototype%"*.
19 | 1. Else if _kind_ is ~async~, then
20 | 1. Let _goal_ be the grammar symbol |AsyncFunctionBody|.
21 | 1. Let _parameterGoal_ be the grammar symbol |FormalParameters[~Yield, +Await]|.
22 | 1. Let _fallbackProto_ be *"%AsyncFunction.prototype%"*.
23 | 1. Else,
24 | 1. Assert: _kind_ is ~asyncGenerator~.
25 | 1. Let _goal_ be the grammar symbol |AsyncGeneratorBody|.
26 | 1. Let _parameterGoal_ be the grammar symbol |FormalParameters[+Yield, +Await]|.
27 | 1. Let _fallbackProto_ be *"%AsyncGeneratorFunction.prototype%"*.
28 | 1. Let _argCount_ be the number of elements in _args_.
29 | 1. Let _P_ be the empty String.
30 | 1. If _argCount_ = 0, let _bodyArg_ be the empty String.
31 | 1. Else if _argCount_ = 1, let _bodyArg_ be _args_[0].
32 | 1. Else,
33 | 1. Assert: _argCount_ > 1.
34 | 1. Let _firstArg_ be _args_[0].
35 | 1. Set _P_ to ? ToString(_firstArg_).
36 | 1. Let _k_ be 1.
37 | 1. Repeat, while _k_ < _argCount_ - 1,
38 | 1. Let _nextArg_ be _args_[_k_].
39 | 1. Let _nextArgString_ be ? ToString(_nextArg_).
40 | 1. Set _P_ to the string-concatenation of _P_, *","* (a comma), and _nextArgString_.
41 | 1. Set _k_ to _k_ + 1.
42 | 1. Let _bodyArg_ be _args_[_k_].
43 | 1. Let _bodyString_ be the string-concatenation of 0x000A (LINE FEED), ? ToString(_bodyArg_), and 0x000A (LINE FEED).
44 | 1. Let _prefix_ be the prefix associated with _kind_ in .
45 | 1. Let _sourceString_ be the string-concatenation of _prefix_, *" anonymous("*, _P_, 0x000A (LINE FEED), *") {"*, _bodyString_, and *"}"*.
46 | 1. Let _sourceText_ be ! StringToCodePoints(_sourceString_).
47 | 1. Perform the following substeps in an implementation-defined order, possibly interleaving parsing and error detection:
48 | 1. Let _parameters_ be the result of parsing ! StringToCodePoints(_P_), using _parameterGoal_ as the goal symbol. Throw a *SyntaxError* exception if the parse fails.
49 | 1. Let _body_ be the result of parsing ! StringToCodePoints(_bodyString_), using _goal_ as the goal symbol. Throw a *SyntaxError* exception if the parse fails.
50 | 1. Let _strict_ be ContainsUseStrict of _body_.
51 | 1. If any static semantics errors are detected for _parameters_ or _body_, throw a *SyntaxError* exception. If _strict_ is *true*, the Early Error rules for UniqueFormalParameters : FormalParameters are applied.
52 | 1. If _strict_ is *true* and IsSimpleParameterList of _parameters_ is *false*, throw a *SyntaxError* exception.
53 | 1. If any element of the BoundNames of _parameters_ also occurs in the LexicallyDeclaredNames of _body_, throw a *SyntaxError* exception.
54 | 1. If _body_ Contains |SuperCall| is *true*, throw a *SyntaxError* exception.
55 | 1. If _parameters_ Contains |SuperCall| is *true*, throw a *SyntaxError* exception.
56 | 1. If _body_ Contains |SuperProperty| is *true*, throw a *SyntaxError* exception.
57 | 1. If _body_ Contains |ClassProperty| is *true*, throw a *SyntaxError* exception.
58 | 1. If _parameters_ Contains |SuperProperty| is *true*, throw a *SyntaxError* exception.
59 | 1. If _parameters_ Contains |ClassProperty| is *true*, throw a *SyntaxError* exception.
60 | 1. If _kind_ is ~generator~ or ~asyncGenerator~, then
61 | 1. If _parameters_ Contains |YieldExpression| is *true*, throw a *SyntaxError* exception.
62 | 1. If _kind_ is ~async~ or ~asyncGenerator~, then
63 | 1. If _parameters_ Contains |AwaitExpression| is *true*, throw a *SyntaxError* exception.
64 | 1. If _strict_ is *true*, then
65 | 1. If BoundNames of _parameters_ contains any duplicate elements, throw a *SyntaxError* exception.
66 | 1. Let _proto_ be ? GetPrototypeFromConstructor(_newTarget_, _fallbackProto_).
67 | 1. Let _realmF_ be the current Realm Record.
68 | 1. Let _scope_ be _realmF_.[[GlobalEnv]].
69 | 1. Let _F_ be ! OrdinaryFunctionCreate(_proto_, _sourceText_, _parameters_, _body_, ~non-lexical-this~, _scope_).
70 | 1. Perform SetFunctionName(_F_, *"anonymous"*).
71 | 1. If _kind_ is ~generator~, then
72 | 1. Let _prototype_ be ! OrdinaryObjectCreate(%GeneratorFunction.prototype.prototype%).
73 | 1. Perform DefinePropertyOrThrow(_F_, *"prototype"*, PropertyDescriptor { [[Value]]: _prototype_, [[Writable]]: *true*, [[Enumerable]]: *false*, [[Configurable]]: *false* }).
74 | 1. Else if _kind_ is ~asyncGenerator~, then
75 | 1. Let _prototype_ be ! OrdinaryObjectCreate(%AsyncGeneratorFunction.prototype.prototype%).
76 | 1. Perform DefinePropertyOrThrow(_F_, *"prototype"*, PropertyDescriptor { [[Value]]: _prototype_, [[Writable]]: *true*, [[Enumerable]]: *false*, [[Configurable]]: *false* }).
77 | 1. Else if _kind_ is ~normal~, perform MakeConstructor(_F_).
78 | 1. NOTE: Functions whose _kind_ is ~async~ are not constructible and do not have a [[Construct]] internal method or a *"prototype"* property.
79 | 1. Return _F_.
80 |
81 |
82 |
CreateDynamicFunction defines a *"prototype"* property on any function it creates whose _kind_ is not ~async~ to provide for the possibility that the function will be used as a constructor.
83 |
84 |
85 |
86 |
87 |
88 |
Kind
Prefix
89 |
~normal~
*"function"*
90 |
~generator~
*"function\*"*
91 |
~async~
*"async function"*
92 |
~asyncGenerator~
*"async function\*"*
93 |
94 |
95 |
96 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 | # ECMAScript class property access expressions
3 |
4 | Class access expressions seek to simplify access to static members of a class as well as provide
5 | access to static members of a class when that class is unnamed:
6 |
7 | ```js
8 | class C {
9 | static f() { ... }
10 |
11 | g() {
12 | class.f();
13 | }
14 | }
15 | ```
16 |
17 | * [Stage 0 Presentation](https://docs.google.com/presentation/d/1VXqGgxq_a0byLuc9yl4jSLR6GlopjvhU_Z0OpZnk6l0/edit?usp=sharing)
18 |
19 |
20 |
21 |
22 | ## Status
23 |
24 | **Stage:** 1
25 | **Champion:** Ron Buckton (@rbuckton)
26 |
27 | _For detailed status of this proposal see [TODO](#todo), below._
28 |
29 |
30 |
31 | ## Authors
32 |
33 | * Ron Buckton (@rbuckton)
34 |
35 |
36 |
37 |
44 |
45 |
46 |
47 | # Motivations
48 |
49 | Today, ECMAScript developers can write classes with static members that can be accessed in one of
50 | two ways:
51 |
52 | - Via the class name:
53 | ```js
54 | class C {
55 | static x() {}
56 | y() { C.x(); }
57 | }
58 | ```
59 | - Via `this` in a static member:
60 | ```js
61 | class C {
62 | static x() {}
63 | static y() { this.x(); }
64 | }
65 | ```
66 |
67 | However, there is no easy mechanism to access class statics in a class that has no name:
68 |
69 | ```js
70 | export default class {
71 | static x() { }
72 | y() {
73 | this.constructor.x(); // Not actually guaranteed to be the correct `x`.
74 | }
75 | }
76 |
77 |
78 | const x = class {
79 | static x() { }
80 | y() {
81 | this.constructor.x(); // Not actually guaranteed to be the correct `x`.
82 | }
83 | }
84 | ```
85 |
86 | It’s not guaranteed to be the correct `x` in the above examples, because you could be
87 | accessing an overridden member of a subclass.
88 |
89 | Also, with current proposal for private static fields and methods, its very easy to
90 | run into errors at runtime when using `this` in a static method:
91 |
92 | ```js
93 | class C {
94 | static #x() {}
95 | static y() { this.#x(); }
96 | }
97 | class D extends C {}
98 | D.y(); // TypeError
99 | ```
100 |
101 |
102 |
103 |
104 | # Syntax
105 |
106 | ```js
107 | // from a non-static method
108 | class C {
109 | static f() { }
110 | g() {
111 | class.f();
112 | class["f"]();
113 | }
114 | }
115 |
116 | // from a static method
117 | class C {
118 | static f() { }
119 | static g() {
120 | class.f();
121 | class["f"]();
122 | }
123 | }
124 |
125 | // with static private members
126 | class C {
127 | static #f() {}
128 | static g() {
129 | class.#f();
130 | }
131 | }
132 | ```
133 |
134 |
135 |
136 | # Semantics
137 |
138 | - Function Environment Records have a new field in Table 15:
139 | > | Field Name | Value | Meaning |
140 | > |:-|:-|:-|
141 | > | \[\[InitialClassObject]] | Object \| **undefined** | If the associated function has `class` property access and is not an _ArrowFunction_, \[\[InitialClassObject]] is the class that the function is bound to as a method. The default value for \[\[InitialClassObject]] is **undefined**. |
142 | - Function Environment Records have a new method in Table 16:
143 | > | Method | Purpose |
144 | > |:-|:-|
145 | > | GetClassBinding() | Return the object that is the base for `class` property access bound in this Environment Record. |
146 | - ECMAScript Function Objects have a new internal slot in Table 27:
147 | > | Interanl Slot | Type | Description |
148 | > |:-|:-|:-|
149 | > | \[\[InitialClassObject]] | Object \| **undefined** | If the function has `class` property access, this is the object where `class` property lookups begin. |
150 | - During ClassDefinitionEvaluation, the class constructor (F) is set as the \[\[InitialClassObject]] on the method.
151 | - During NewFunctionEnvironment, the \[\[InitialClassObject]] is copied from the method (F) to envRec.\[\[InitialClassObject]].
152 | - Arrow functions use the \[\[InitialClassObject]] of their containing lexical environment (similar to `super` and `this`).
153 | - When evaluating ``ClassProperty: `class` `.` IdentifierName`` we return a new Reference with the following properties:
154 | - The referenced name component is the StringValue of _IdentifierName_.
155 | - The base value component is the \[\[InitialClassObject]] of GetThisEnvironment().
156 | - When evaluating ``ClassProperty: `class` `[` Expression `]` `` we return a new Reference with the following properties:
157 | - The referenced name component is the result of calling ?ToPropertyKey on the result of calling GetValue on the result of evaluating _Expression_.
158 | - The base value component is the \[\[InitialClassObject]] of GetThisEnvironment().
159 | - When evaluating ``ClassProperty: `class` `.` PrivateIdentifier`` we perform the following steps:
160 | 1. Let `fieldNameString` be the StringValue of _PrivateIdentifier_.
161 | 2. Let `bv` be the \[\[InitialClassObject]] of GetThisEnvironment().
162 | 3. Return ?[MakePrivateReference](https://tc39.es/proposal-class-fields/#sec-makeprivatereference)( `bv`, `fieldNameString` )
163 | - `class` bindings are only available in the following declarations:
164 | - A method of a class.
165 | - An accessor of a class.
166 | - A field initializer of a class.
167 | - The constructor of a class.
168 | - A class's `static` intialization block (see http://github.com/tc39/proposal-class-static-block)
169 | - An *ArrowFunction* in any of these declarations.
170 | - `class` bindings are *not* valid in any of the following declarations:
171 | - A *FunctionDeclaration* or *FunctionExpression*.
172 | - A method of an object literal.
173 | - An accessor of an object literal.
174 | - Any execution context not nested within a lexical `class` declaration, including module or global scope.
175 | - *NOTE:* This aligns with the behavior of `super`.
176 |
177 |
178 |
179 |
180 | ## Examples
181 |
182 | ### Property Access
183 |
184 | In class methods or the class constructor, getting the value of `class.x` always refers to the value of the property `x` on the
185 | containing lexical class:
186 |
187 | ```js
188 | class Base {
189 | static f() {
190 | console.log(`this: ${this.name}, class: ${class.name})`);
191 | }
192 | }
193 | class Sub extends Base {
194 | }
195 |
196 | Base.f(); // this: Base, class: Base
197 | Sub.f(); // this: Sub, class: Base
198 | Base.f.call({ name: "Other" }); // this: Other, class: Base
199 | ```
200 |
201 | This behavior provides the following benefits:
202 |
203 | - Able to reference static members of the containing lexical class without needing to repeat the class name.
204 | - Able to reference static members of an anonymous class declaration or expression:
205 | ```js
206 | export default class {
207 | static f() { ... }
208 | g() { class.f(); }
209 | }
210 | ```
211 |
212 | ### Property Assignment
213 |
214 | In class methods or the class constructor, setting the value of `class.x` always updates the value of the property `x` on the
215 | containing lexical class:
216 |
217 | ```js
218 | function print(F) {
219 | const { name, x, y } = F;
220 | const hasX = F.hasOwnProperty("x") ? "own" : "inherited";
221 | const hasY = F.hasOwnProperty("y") ? "own" : "inherited";
222 | console.log(`${name}.x: ${x} (${hasX}), ${name}.y: ${y} (${hasY})`);
223 | }
224 |
225 | class Base {
226 | static f() {
227 | this.x++;
228 | class.y++;
229 | }
230 | }
231 |
232 | Base.x = 0;
233 | Base.y = 0;
234 |
235 | class Sub extends Base {
236 | }
237 |
238 | print(Base); // Base.x: 0 (own), Base.y: 0 (own)
239 | print(Sub); // Sub.x: 0 (inherited), Sub.y: 0 (inherited)
240 |
241 | Base.f();
242 |
243 | print(Base); // Base.x: 1 (own), Base.y: 1 (own)
244 | print(Sub); // Sub.x: 1 (inherited), Sub.y: 1 (inherited)
245 |
246 | Sub.f();
247 |
248 | print(Base); // Base.x: 1 (own), Base.y: 2 (own)
249 | print(Sub); // Sub.x: 2 (own), Sub.y: 2 (inherited)
250 |
251 | Base.f();
252 |
253 | print(Base); // Base.x: 2 (own), Base.y: 3 (own)
254 | print(Sub); // Sub.x: 2 (own), Sub.y: 3 (inherited)
255 | ```
256 |
257 | This behavior provides the following benefits:
258 |
259 | - Assignments always occur on the current lexical class, which should be unsurprising to users.
260 |
261 | ### Method Invocation
262 |
263 | Invoking `class.x()` in a method, an initializer, or in the constructor uses the value of containing lexical class as the receiver:
264 |
265 | ```js
266 | class Base {
267 | static f() {
268 | console.log(`this.name: ${this.name}, class.name: ${class.name})`);
269 | }
270 | static g() {
271 | class.f();
272 | }
273 | h() {
274 | class.f();
275 | }
276 | }
277 | class Sub extends Base {
278 | }
279 |
280 | Base.g(); // this: Base, class: Base
281 | Sub.g(); // this: Sub, class: Base
282 | Base.g.call({ name: "Other" }); // this: Other, class: Base
283 |
284 | let b = new Base();
285 | let s = new Sub();
286 | b.h(); // this: Base, class: Base
287 | s.h(); // this: Sub, class: Base
288 | b.h.call({ name: "Other" }); // this: Other, class: Base
289 | ```
290 |
291 | ### Invalid usage
292 |
293 | ```js
294 | class C {
295 | static x = 1;
296 | constructor() {
297 | function f() {
298 | return class.x; // function has no access to `class.`
299 | }
300 | f(); // throws TypeError
301 |
302 | const obj = {
303 | method() {
304 | return class.x; // method of object literal has no access to `class`.
305 | }
306 | };
307 | obj.method(); // throws TypeError
308 | }
309 | }
310 | ```
311 |
312 |
313 |
314 |
315 |
320 |
321 |
322 |
323 | # Grammar
324 |
325 | ```grammarkdown
326 | MemberExpression[Yield, Await] :
327 | ClassProperty[?Yield, ?Await]
328 |
329 | ClassProperty[Yield, Await] :
330 | `class` `[` Expression[+In, ?Yield, ?Await] `]`
331 | `class` `.` IdentifierName
332 | `class` `.` PrivateIdentifier
333 | ```
334 |
335 |
336 | # Relationship to Other Proposals
337 |
338 | ## Class Fields
339 |
340 | This proposal can easily align with the current class fields proposal, providing easier access to static fields without unexpected behavior:
341 |
342 | ```js
343 | class Base {
344 | static counter = 0;
345 | id = class.counter++; // `Base` is used as `this`
346 | }
347 |
348 | class Sub extends Base {
349 | }
350 |
351 | console.log(new Base().id); // 0
352 | console.log(new Sub().id); // 1
353 | console.log(Base.counter); // 2
354 | console.log(Sub.counter); // 2
355 | ```
356 |
357 |
358 | ## Class Private Fields
359 |
360 | In addition to private methods, this proposal can also align with the current proposals for class private fields, providing
361 | access to class static private state without introducing TypeErrors due to incorrect `this`:
362 |
363 | ```js
364 | class Base {
365 | static #counter = 0;
366 | static increment() {
367 | return class.#counter++;
368 | }
369 | }
370 |
371 | class Sub extends Base {
372 | }
373 |
374 | console.log(Base.increment()); // 0
375 | console.log(Sub.increment()); // 1
376 | console.log(Base.increment()); // 2
377 | ```
378 |
379 | ## Class Private Methods
380 |
381 | One of the benefits of `class` access expressions is that they guarantee the correct reference is used when accessing static private members. Special care must be taken, however, when invoking private and non-private static methods using `class` access expressions, as the `this` binding within the invoked method will be the lexical class declaration:
382 |
383 | ```js
384 | class Base {
385 | static #counter = 0;
386 | static #increment() {
387 | class.#counter++;
388 | this.printCounter();
389 | }
390 | static doIncrement() {
391 | class.#increment();
392 | }
393 | static printCounter() {
394 | console.log(class.#counter);
395 | }
396 | }
397 | class Sub extends Base {
398 | static printCounter() {
399 | console.log("Custom Counter");
400 | super.printCounter();
401 | }
402 | }
403 |
404 | Base.doIncrement(); // prints: 1
405 | Sub.doIncrement(); // prints: 2
406 | ```
407 |
408 | In the example above, `Sub`'s overriden `printCounter` is never invoked. Such method calls would need to be rewritten:
409 |
410 | ```js
411 | // option 1:
412 | class Base {
413 | ...
414 | static #increment() {
415 | ...
416 | }
417 | static doIncrement() {
418 | class.#increment.call(this);
419 | }
420 | }
421 |
422 | // option 2:
423 | class Base {
424 | ...
425 | static #increment(C) {
426 | ...
427 | C.printCounter();
428 | }
429 | ...
430 | static doIncrement() {
431 | class.#increment(this);
432 | }
433 | }
434 | ```
435 |
436 | This is due to the fact that `class.` in this example is essentially a substitute for `Base.`, therefore `Base` becomes the receiver in these method calls.
437 |
438 |
439 |
440 |
447 |
448 |
449 |
450 |
457 |
458 |
459 |
460 | # TODO
461 |
462 | The following is a high-level list of tasks to progress through each stage of the [TC39 proposal process](https://tc39.github.io/process-document/):
463 |
464 | ### Stage 1 Entrance Criteria
465 |
466 | * [x] Identified a "[champion][Champion]" who will advance the addition.
467 | * [x] [Prose][Prose] outlining the problem or need and the general shape of a solution.
468 | * [x] Illustrative [examples][Examples] of usage.
469 | * [x] High-level [API][API].
470 |
471 | ### Stage 2 Entrance Criteria
472 |
473 | * [x] [Initial specification text][Specification].
474 | * [ ] [Transpiler support][Transpiler] (_Optional_).
475 |
476 | ### Stage 3 Entrance Criteria
477 |
478 | * [ ] [Complete specification text][Specification].
479 | * [ ] Designated reviewers have [signed off][Stage3ReviewerSignOff] on the current spec text.
480 | * [ ] The ECMAScript editor has [signed off][Stage3EditorSignOff] on the current spec text.
481 |
482 | ### Stage 4 Entrance Criteria
483 |
484 | * [ ] [Test262](https://github.com/tc39/test262) acceptance tests have been written for mainline usage scenarios and [merged][Test262PullRequest].
485 | * [ ] Two compatible implementations which pass the acceptance tests: [\[1\]][Implementation1], [\[2\]][Implementation2].
486 | * [ ] A [pull request][Ecma262PullRequest] has been sent to tc39/ecma262 with the integrated spec text.
487 | * [ ] The ECMAScript editor has signed off on the [pull request][Ecma262PullRequest].
488 |
489 |
490 |
491 |
492 | [Process]: https://tc39.github.io/process-document/
493 | [Proposals]: https://github.com/tc39/proposals/
494 | [Grammarkdown]: http://github.com/rbuckton/grammarkdown#readme
495 | [Champion]: #status
496 | [Prose]: #motivations
497 | [Examples]: #examples
498 | [API]: #api
499 | [Specification]: https://tc39.es/proposal-class-access-expressions
500 |
501 |
502 | [Transpiler]: #todo
503 | [Stage3ReviewerSignOff]: #todo
504 | [Stage3EditorSignOff]: #todo
505 | [Test262PullRequest]: #todo
506 | [Implementation1]: #todo
507 | [Implementation2]: #todo
508 | [Ecma262PullRequest]: #todo
509 |
510 |
--------------------------------------------------------------------------------