Skip to content

Check destructuring validity the same way element accesses and indexed accesses are checked#24700

Merged
weswigham merged 6 commits intomicrosoft:masterfrom
weswigham:generic-mapped-destructuring
Nov 1, 2018
Merged

Check destructuring validity the same way element accesses and indexed accesses are checked#24700
weswigham merged 6 commits intomicrosoft:masterfrom
weswigham:generic-mapped-destructuring

Conversation

@weswigham
Copy link
Copy Markdown
Member

@weswigham weswigham commented Jun 5, 2018

Fixes #24661

This causes some error messages to change to match the indexing case (IMO, good for consistency, since the messages were almost the same). To preserve some semantics destructuring had with private/protected members of generics (eg, this), some shuffling of apparent types had to be done as well. Lastly, we seem to actually pick up a few error cases we somehow just missed before, eg, destructuring with a string computed name when there's no string index signature.

@weswigham weswigham requested review from ahejlsberg and mhegazy June 7, 2018 17:47
~
!!! error TS2448: Block-scoped variable 'a' used before its declaration.
~
!!! error TS2538: Type 'any' cannot be used as an index type.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This doesn't feel like a legal error, but it seems like we're only issuing it when there's already an error on the same node. Is there an issue with the error type leaking out into an error message?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Most certainly. It's because we choose to consider indexing with any an error today (esp. if the thing being indexed has no index signatures), but destructuring accesses don't flag that right now. This PR aligns them.

@RyanCavanaugh RyanCavanaugh added this to the TypeScript 3.2 milestone Sep 17, 2018
Comment thread src/compiler/checker.ts
? getLateBoundNameFromType(indexType)
: accessExpression && checkThatExpressionIsProperSymbolReference(accessExpression.argumentExpression, indexType, /*reportError*/ false)
? getPropertyNameForKnownSymbolName(idText((<PropertyAccessExpression>accessExpression.argumentExpression).name))
: accessNode && isPropertyName(accessNode)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think you need this case.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Needed to handle well-known symbol names, which are not normal property names or unique symbols:

let { [Symbol.iterator]: destructured } = []

Comment thread src/compiler/checker.ts Outdated
}

function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode, missingType = accessNode ? errorType : unknownType): Type {
function getIndexedAccessType(objectType: Type, indexType: Type, accessNode?: ElementAccessExpression | IndexedAccessTypeNode | PropertyName, useApparentObjectType?: boolean, missingType = accessNode ? errorType : unknownType): Type {
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No extra flag please.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's now gone, and I'm using the raw apparent type as the input directly instead. The downside is that error messages now reference the apparent type instead of the original type, too.

Copy link
Copy Markdown
Member

@ahejlsberg ahejlsberg left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just one minor change, otherwise looks good.

Comment thread src/compiler/checker.ts Outdated
return errorType;
}
const exprType = isComputedPropertyName(name)
? checkExpression(name.expression)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Use checkComputedPropertyName here.

@weswigham weswigham merged commit deeee77 into microsoft:master Nov 1, 2018
@weswigham weswigham deleted the generic-mapped-destructuring branch November 1, 2018 20:46
@microsoft microsoft locked as resolved and limited conversation to collaborators Oct 21, 2025
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants