Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Is MemberExpression a Pattern? #162

Open
cpcallen opened this issue Apr 3, 2017 · 3 comments
Open

Is MemberExpression a Pattern? #162

cpcallen opened this issue Apr 3, 2017 · 3 comments

Comments

@cpcallen
Copy link

cpcallen commented Apr 3, 2017

es5.md says:

Nevertheless, for ES5, the only Pattern subtype is Identifier.

But this is not true; MemberExpression is defined thusly:

interface MemberExpression <: Expression, Pattern {
    type: "MemberExpression";
    object: Expression;
    property: Expression;
    computed: boolean;
}

This is great, because ForInStatement is defined thusly:

interface ForInStatement <: Statement {
    type: "ForInStatement";
    left: VariableDeclaration |  Pattern;
    right: Expression;
    body: Statement;
}

…and indeed we can use a MemberExpression in a ForInStatement, and it works exactly as you would expect:

var o = {foo: bar}
var a = {a:1, b:2, c:3}
for(o.foo in a) { alert(o.foo) }

However, es5.md also declares Function.params as [Pattern] and CatchClause.param as Pattern, and ECMA262 5.1 clearly restricts these to [Identifier] and Identifier respectively, so perhaps it is the definitions of MemberExpression and ForInStatement which are wrong?

(Actually, ForInStatement is definitely wrong; per @michaelficarra's reasoning in #160, ForInStatement.Left can actually be any Expression (see https://www.ecma-international.org/ecma-262/5.1/#sec-12.6.4, where it is a LeftHandSideExpression which in turn can be any expression), which means that the following bizarre construction is (syntactically) legal:

for(f() in myObject) { /* ... */ }

…and for consistency should be representable as an estree.)

I am not sure which of these solutions is preferable, either in general or specifically in terms of impact on the the estree es201[567].md specs; unfortunately I have not managed to get my head around the full ECMA262 7.0 spec sufficiently to understand what precisely is now allowed in function and catch clause parameter declarations.

@RReverser
Copy link
Member

Sounds like duplicate of #161

@cpcallen
Copy link
Author

cpcallen commented Apr 3, 2017

@RReverser: you are basically correct; I had not seen that issue. Apologies for opening a near-duplicate.

I do think it would be helpful if the description of Pattern was consistent with the actual definition, however, so I will leave this issue open so that that at least might be addressed—perhaps by someone with a better understanding of the legacy, interoperability and post-5.1 issues than me.

(One criteria for a good enough description of Pattern might be "prevents further well-meaning but ill-informed duplicates of #161"...)

@RReverser
Copy link
Member

I agree, it's just that neither of proposed PRs currently fixes it correctly - in both cases, you end up with either breaking correct representation or duplicating same lists of actual node types in every field.

While ESTree spec itself is really more of representation spec rather than precise type system (this is best left to ESTree's TypeScript definitions which describe relations between different types more correctly), this is something we could fix in this specific case by creating a descendant of Pattern called e.g. DeclarationPattern and using it in these very few contexts where only declaration patterns are allowed and not any assignable ones (variable declaration, function param list and such).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants