-
Notifications
You must be signed in to change notification settings - Fork 636
Add {}/class-expression expandos #885
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
base: main
Are you sure you want to change the base?
Conversation
Also fix up this-container tracking and assignment-declaration contextual typing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull Request Overview
Adds support for “expando” properties on empty object literals and class expressions in JavaScript, including nested expandos and element-access syntax. Key changes include binder enhancements to recognize and bind expando assignments, checker updates to handle expando types without circularity, and updated test baselines to reflect new type, symbol, and error outputs.
- Introduce
bindExpandoPropertyAssignment
withgetInitializerSymbol
andisExpandoInitializer
in the binder - Extend checker to skip the usual object-literal paths for expandos and adjust contextual typing
- Update utilities and AST to recognize JS entity names and improve error context
- Refresh numerous testdata baselines for types, symbols, and errors
Reviewed Changes
Copilot reviewed 240 out of 240 changed files in this pull request and generated 2 comments.
Show a summary per file
File | Description |
---|---|
internal/checker/checker.go | Skip original literal-check paths for expando object literals and adjust widening/contextual typing logic |
internal/binder/binder.go | Add ContainerFlagsIsThisContainer , bindExpandoPropertyAssignment , getInitializerSymbol , and helper logic for expandos |
internal/ast/utilities.go | Extend GetAssignmentDeclarationKind and entity-name checks to include JS and element access patterns |
internal/ast/ast.go | Improve panic messages in Node.Expression and Node.Arguments with kind info |
testdata/baselines/reference/submodule/compiler/jsEnumCrossFileExport.types | Updated expected types for enum and expando export support |
testdata/baselines/reference/submodule/compiler/jsEnumCrossFileExport.symbols.diff | Adjusted symbol diff to include new expando symbols |
testdata/baselines/reference/submodule/compiler/jsEnumCrossFileExport.symbols | Updated baseline symbols for cross-file enum exports |
testdata/baselines/reference/submodule/compiler/jsEnumCrossFileExport.errors.txt | Refined expected errors after enabling expandos |
testdata/baselines/reference/submodule/compiler/jsElementAccessNoContextualTypeCrash.types | Added expected types for Common.localize expando via element access |
testdata/baselines/reference/submodule/compiler/jsElementAccessNoContextualTypeCrash.symbols.diff | Updated symbol diff for element-accessed expandos |
testdata/baselines/reference/submodule/compiler/jsElementAccessNoContextualTypeCrash.symbols | Refreshed symbols baseline for Common.localize |
testdata/baselines/reference/submodule/compiler/jsElementAccessNoContextualTypeCrash.errors.txt | Adjusted errors for the Common assignment when widening types |
testdata/baselines/reference/submodule/compiler/ensureNoCrashExportAssignmentDefineProperrtyPotentialMerge.types | Updated types for module.exports and Object.defineProperty expandos |
testdata/baselines/reference/submodule/compiler/ensureNoCrashExportAssignmentDefineProperrtyPotentialMerge.symbols.diff | Added symbol diffs for merged export assignments |
testdata/baselines/reference/submodule/compiler/ensureNoCrashExportAssignmentDefineProperrtyPotentialMerge.symbols | Refreshed symbols baseline after merging defineProperty and export assignments |
testdata/baselines/reference/submodule/compiler/ensureNoCrashExportAssignmentDefineProperrtyPotentialMerge.errors.txt | Cleaned up expected error counts and messages |
testdata/baselines/reference/submodule/compiler/classFieldSuperAccessibleJs1.types | Updated expected types for super-accessible static class fields |
testdata/baselines/reference/submodule/compiler/classFieldSuperAccessibleJs1.symbols.diff | Adjusted symbol diffs for super.blah2 |
testdata/baselines/reference/submodule/compiler/classFieldSuperAccessibleJs1.symbols | Refreshed symbols baseline for class-field super access |
testdata/baselines/reference/submodule/compiler/classFieldSuperAccessibleJs1.errors.txt | Removed obsolete errors now resolved by expando support |
Comments suppressed due to low confidence (2)
internal/binder/binder.go:39
- [nitpick] The flag name
ContainerFlagsIsThisContainer
is slightly verbose and inconsistent with other flags (dropIs
or reorder words). ConsiderContainerFlagsThisContainer
for consistency.
ContainerFlagsIsThisContainer ContainerFlags = 1 << 8
internal/ast/utilities.go:1478
- [nitpick] The parameter
allowJS
may be unclear in intent; consider renaming to something likeallowInJSContext
orincludeJS
to clarify its effect.
func IsEntityNameExpressionEx(node *Node, allowJS bool) bool {
@@ -16926,6 +16931,11 @@ func (c *Checker) getWidenedTypeWithContext(t *Type, context *WideningContext) * | |||
case t.flags&(TypeFlagsAny|TypeFlagsNullable) != 0: | |||
result = c.anyType | |||
case isObjectLiteralType(t): | |||
// expando object literal types do not widen to prevent circular checking (but should, ideally) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is a TODO that I'll get back to later
if localsContainer != nil { | ||
local := localsContainer.Locals[name] | ||
if local != nil { | ||
if localsContainer := container.LocalsContainerData(); localsContainer != nil { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just a style improvement--at least I hope it's an improvement.
This PR adds support for expando properties on
{}
and class expressions in Javascript. It also adds support for expandos on expandos in Javascript:It also works with element accesses as well as property accesses.
Implementation notes
thisParentContainer
tracking was not complete, so it relies on getThisContainer, which isn't safe to use in the binder because not all parent pointers are set. I added a specific ContainerFlags forthis
, and the resulting code should be simpler and safer.{}
expandos is different because the exports are on the object literal, not the declaring variable. The binding is now consistent between{}, class, function
expressions, and the checker code to support the old way would be at least as bad.{}
means that those expando properties don't widen. I'll return to this later.The binder diff is a lot easier to read with whitespace ignored since I pulled out some code into a separate function.