@@ -8402,12 +8402,12 @@ namespace ts {
8402
8402
}
8403
8403
8404
8404
function isNullOrUndefined(node: Expression) {
8405
- const expr = skipParentheses(node);
8405
+ const expr = skipParentheses(node, /*excludeJSDocTypeAssertions*/ true );
8406
8406
return expr.kind === SyntaxKind.NullKeyword || expr.kind === SyntaxKind.Identifier && getResolvedSymbol(expr as Identifier) === undefinedSymbol;
8407
8407
}
8408
8408
8409
8409
function isEmptyArrayLiteral(node: Expression) {
8410
- const expr = skipParentheses(node);
8410
+ const expr = skipParentheses(node, /*excludeJSDocTypeAssertions*/ true );
8411
8411
return expr.kind === SyntaxKind.ArrayLiteralExpression && (expr as ArrayLiteralExpression).elements.length === 0;
8412
8412
}
8413
8413
@@ -22968,7 +22968,7 @@ namespace ts {
22968
22968
}
22969
22969
22970
22970
function isFalseExpression(expr: Expression): boolean {
22971
- const node = skipParentheses(expr);
22971
+ const node = skipParentheses(expr, /*excludeJSDocTypeAssertions*/ true );
22972
22972
return node.kind === SyntaxKind.FalseKeyword || node.kind === SyntaxKind.BinaryExpression && (
22973
22973
(node as BinaryExpression).operatorToken.kind === SyntaxKind.AmpersandAmpersandToken && (isFalseExpression((node as BinaryExpression).left) || isFalseExpression((node as BinaryExpression).right)) ||
22974
22974
(node as BinaryExpression).operatorToken.kind === SyntaxKind.BarBarToken && isFalseExpression((node as BinaryExpression).left) && isFalseExpression((node as BinaryExpression).right));
@@ -23290,7 +23290,7 @@ namespace ts {
23290
23290
}
23291
23291
23292
23292
function narrowTypeByAssertion(type: Type, expr: Expression): Type {
23293
- const node = skipParentheses(expr);
23293
+ const node = skipParentheses(expr, /*excludeJSDocTypeAssertions*/ true );
23294
23294
if (node.kind === SyntaxKind.FalseKeyword) {
23295
23295
return unreachableNeverType;
23296
23296
}
@@ -25874,7 +25874,9 @@ namespace ts {
25874
25874
case SyntaxKind.ParenthesizedExpression: {
25875
25875
// Like in `checkParenthesizedExpression`, an `/** @type {xyz} */` comment before a parenthesized expression acts as a type cast.
25876
25876
const tag = isInJSFile(parent) ? getJSDocTypeTag(parent) : undefined;
25877
- return tag ? getTypeFromTypeNode(tag.typeExpression.type) : getContextualType(parent as ParenthesizedExpression, contextFlags);
25877
+ return !tag ? getContextualType(parent as ParenthesizedExpression, contextFlags) :
25878
+ isJSDocTypeTag(tag) && isConstTypeReference(tag.typeExpression.type) ? tryFindWhenConstTypeReference(parent as ParenthesizedExpression) :
25879
+ getTypeFromTypeNode(tag.typeExpression.type);
25878
25880
}
25879
25881
case SyntaxKind.NonNullExpression:
25880
25882
return getContextualType(parent as NonNullExpression, contextFlags);
@@ -32883,8 +32885,10 @@ namespace ts {
32883
32885
}
32884
32886
32885
32887
function isTypeAssertion(node: Expression) {
32886
- node = skipParentheses(node);
32887
- return node.kind === SyntaxKind.TypeAssertionExpression || node.kind === SyntaxKind.AsExpression;
32888
+ node = skipParentheses(node, /*excludeJSDocTypeAssertions*/ true);
32889
+ return node.kind === SyntaxKind.TypeAssertionExpression ||
32890
+ node.kind === SyntaxKind.AsExpression ||
32891
+ isJSDocTypeAssertion(node);
32888
32892
}
32889
32893
32890
32894
function checkDeclarationInitializer(declaration: HasExpressionInitializer, contextualType?: Type | undefined) {
@@ -32959,6 +32963,7 @@ namespace ts {
32959
32963
function isConstContext(node: Expression): boolean {
32960
32964
const parent = node.parent;
32961
32965
return isAssertionExpression(parent) && isConstTypeReference(parent.type) ||
32966
+ isJSDocTypeAssertion(parent) && isConstTypeReference(getJSDocTypeAssertionType(parent)) ||
32962
32967
(isParenthesizedExpression(parent) || isArrayLiteralExpression(parent) || isSpreadElement(parent)) && isConstContext(parent) ||
32963
32968
(isPropertyAssignment(parent) || isShorthandPropertyAssignment(parent) || isTemplateSpan(parent)) && isConstContext(parent.parent);
32964
32969
}
@@ -33171,7 +33176,14 @@ namespace ts {
33171
33176
}
33172
33177
33173
33178
function getQuickTypeOfExpression(node: Expression) {
33174
- const expr = skipParentheses(node);
33179
+ let expr = skipParentheses(node, /*excludeJSDocTypeAssertions*/ true);
33180
+ if (isJSDocTypeAssertion(expr)) {
33181
+ const type = getJSDocTypeAssertionType(expr);
33182
+ if (!isConstTypeReference(type)) {
33183
+ return getTypeFromTypeNode(type);
33184
+ }
33185
+ }
33186
+ expr = skipParentheses(node);
33175
33187
// Optimize for the common case of a call to a function with a single non-generic call
33176
33188
// signature where we can just fetch the return type without checking the arguments.
33177
33189
if (isCallExpression(expr) && expr.expression.kind !== SyntaxKind.SuperKeyword && !isRequireCall(expr, /*checkArgumentIsStringLiteralLike*/ true) && !isSymbolOrSymbolForCall(expr)) {
@@ -33258,9 +33270,9 @@ namespace ts {
33258
33270
}
33259
33271
33260
33272
function checkParenthesizedExpression(node: ParenthesizedExpression, checkMode?: CheckMode): Type {
33261
- const tag = isInJSFile(node) ? getJSDocTypeTag (node) : undefined;
33262
- if (tag) {
33263
- return checkAssertionWorker(tag.typeExpression. type, tag.typeExpression. type, node.expression, checkMode);
33273
+ if (isJSDocTypeAssertion (node)) {
33274
+ const type = getJSDocTypeAssertionType(node);
33275
+ return checkAssertionWorker(type, type, node.expression, checkMode);
33264
33276
}
33265
33277
return checkExpression(node.expression, checkMode);
33266
33278
}
@@ -36210,7 +36222,7 @@ namespace ts {
36210
36222
if (getFalsyFlags(type)) return;
36211
36223
36212
36224
const location = isBinaryExpression(condExpr) ? condExpr.right : condExpr;
36213
- if (isPropertyAccessExpression(location) && isAssertionExpression(skipParentheses( location.expression) )) {
36225
+ if (isPropertyAccessExpression(location) && isTypeAssertion( location.expression)) {
36214
36226
return;
36215
36227
}
36216
36228
0 commit comments