@@ -142,7 +142,6 @@ namespace ts {
142
142
const voidType = createIntrinsicType(TypeFlags.Void, "void");
143
143
const neverType = createIntrinsicType(TypeFlags.Never, "never");
144
144
const silentNeverType = createIntrinsicType(TypeFlags.Never, "never");
145
- const stringOrNumberType = getUnionType([stringType, numberType]);
146
145
147
146
const emptyObjectType = createAnonymousType(undefined, emptySymbols, emptyArray, emptyArray, undefined, undefined);
148
147
@@ -3156,38 +3155,10 @@ namespace ts {
3156
3155
}
3157
3156
3158
3157
function getTypeForVariableLikeDeclarationFromJSDocComment(declaration: VariableLikeDeclaration) {
3159
- const jsDocType = getJSDocTypeForVariableLikeDeclarationFromJSDocComment (declaration);
3160
- if (jsDocType ) {
3161
- return getTypeFromTypeNode(jsDocType );
3158
+ const jsdocType = getJSDocType (declaration);
3159
+ if (jsdocType ) {
3160
+ return getTypeFromTypeNode(jsdocType );
3162
3161
}
3163
- }
3164
-
3165
- function getJSDocTypeForVariableLikeDeclarationFromJSDocComment(declaration: VariableLikeDeclaration): JSDocType {
3166
- // First, see if this node has an @type annotation on it directly.
3167
- const typeTag = getJSDocTypeTag(declaration);
3168
- if (typeTag && typeTag.typeExpression) {
3169
- return typeTag.typeExpression.type;
3170
- }
3171
-
3172
- if (declaration.kind === SyntaxKind.VariableDeclaration &&
3173
- declaration.parent.kind === SyntaxKind.VariableDeclarationList &&
3174
- declaration.parent.parent.kind === SyntaxKind.VariableStatement) {
3175
-
3176
- // @type annotation might have been on the variable statement, try that instead.
3177
- const annotation = getJSDocTypeTag(declaration.parent.parent);
3178
- if (annotation && annotation.typeExpression) {
3179
- return annotation.typeExpression.type;
3180
- }
3181
- }
3182
- else if (declaration.kind === SyntaxKind.Parameter) {
3183
- // If it's a parameter, see if the parent has a jsdoc comment with an @param
3184
- // annotation.
3185
- const paramTag = getCorrespondingJSDocParameterTag(<ParameterDeclaration>declaration);
3186
- if (paramTag && paramTag.typeExpression) {
3187
- return paramTag.typeExpression.type;
3188
- }
3189
- }
3190
-
3191
3162
return undefined;
3192
3163
}
3193
3164
@@ -3217,9 +3188,11 @@ namespace ts {
3217
3188
}
3218
3189
}
3219
3190
3220
- // A variable declared in a for..in statement is always of type string
3191
+ // A variable declared in a for..in statement is of type string, or of type keyof T when the
3192
+ // right hand expression is of a type parameter type.
3221
3193
if (declaration.parent.parent.kind === SyntaxKind.ForInStatement) {
3222
- return stringType;
3194
+ const indexType = getIndexType(checkNonNullExpression((<ForInStatement>declaration.parent.parent).expression));
3195
+ return indexType.flags & TypeFlags.Index ? indexType : stringType;
3223
3196
}
3224
3197
3225
3198
if (declaration.parent.parent.kind === SyntaxKind.ForOfStatement) {
@@ -3455,9 +3428,9 @@ namespace ts {
3455
3428
declaration.kind === SyntaxKind.PropertyAccessExpression && declaration.parent.kind === SyntaxKind.BinaryExpression) {
3456
3429
// Use JS Doc type if present on parent expression statement
3457
3430
if (declaration.flags & NodeFlags.JavaScriptFile) {
3458
- const typeTag = getJSDocTypeTag (declaration.parent);
3459
- if (typeTag && typeTag.typeExpression ) {
3460
- return links.type = getTypeFromTypeNode(typeTag.typeExpression.type );
3431
+ const jsdocType = getJSDocType (declaration.parent);
3432
+ if (jsdocType ) {
3433
+ return links.type = getTypeFromTypeNode(jsdocType );
3461
3434
}
3462
3435
}
3463
3436
const declaredTypes = map(symbol.declarations,
@@ -4688,7 +4661,6 @@ namespace ts {
4688
4661
t.flags & TypeFlags.NumberLike ? globalNumberType :
4689
4662
t.flags & TypeFlags.BooleanLike ? globalBooleanType :
4690
4663
t.flags & TypeFlags.ESSymbol ? getGlobalESSymbolType() :
4691
- t.flags & TypeFlags.Index ? stringOrNumberType :
4692
4664
t;
4693
4665
}
4694
4666
@@ -4901,15 +4873,16 @@ namespace ts {
4901
4873
if (node.type && node.type.kind === SyntaxKind.JSDocOptionalType) {
4902
4874
return true;
4903
4875
}
4876
+ const paramTags = getJSDocParameterTags(node);
4877
+ if (paramTags) {
4878
+ for (const paramTag of paramTags) {
4879
+ if (paramTag.isBracketed) {
4880
+ return true;
4881
+ }
4904
4882
4905
- const paramTag = getCorrespondingJSDocParameterTag(node);
4906
- if (paramTag) {
4907
- if (paramTag.isBracketed) {
4908
- return true;
4909
- }
4910
-
4911
- if (paramTag.typeExpression) {
4912
- return paramTag.typeExpression.type.kind === SyntaxKind.JSDocOptionalType;
4883
+ if (paramTag.typeExpression) {
4884
+ return paramTag.typeExpression.type.kind === SyntaxKind.JSDocOptionalType;
4885
+ }
4913
4886
}
4914
4887
}
4915
4888
}
@@ -5920,8 +5893,7 @@ namespace ts {
5920
5893
function getIndexType(type: Type): Type {
5921
5894
return type.flags & TypeFlags.TypeParameter ? getIndexTypeForTypeParameter(<TypeParameter>type) :
5922
5895
getObjectFlags(type) & ObjectFlags.Mapped ? getConstraintTypeFromMappedType(<MappedType>type) :
5923
- type.flags & TypeFlags.Any || getIndexInfoOfType(type, IndexKind.String) ? stringOrNumberType :
5924
- getIndexInfoOfType(type, IndexKind.Number) ? getUnionType([numberType, getLiteralTypeFromPropertyNames(type)]) :
5896
+ type.flags & TypeFlags.Any || getIndexInfoOfType(type, IndexKind.String) ? stringType :
5925
5897
getLiteralTypeFromPropertyNames(type);
5926
5898
}
5927
5899
@@ -6039,19 +6011,19 @@ namespace ts {
6039
6011
const id = objectType.id + "," + indexType.id;
6040
6012
return indexedAccessTypes[id] || (indexedAccessTypes[id] = createIndexedAccessType(objectType, indexType));
6041
6013
}
6042
- const apparentType = getApparentType(objectType);
6014
+ const apparentObjectType = getApparentType(objectType);
6043
6015
if (indexType.flags & TypeFlags.Union && !(indexType.flags & TypeFlags.Primitive)) {
6044
6016
const propTypes: Type[] = [];
6045
6017
for (const t of (<UnionType>indexType).types) {
6046
- const propType = getPropertyTypeForIndexType(apparentType , t, accessNode, /*cacheSymbol*/ false);
6018
+ const propType = getPropertyTypeForIndexType(apparentObjectType , t, accessNode, /*cacheSymbol*/ false);
6047
6019
if (propType === unknownType) {
6048
6020
return unknownType;
6049
6021
}
6050
6022
propTypes.push(propType);
6051
6023
}
6052
6024
return getUnionType(propTypes);
6053
6025
}
6054
- return getPropertyTypeForIndexType(apparentType , indexType, accessNode, /*cacheSymbol*/ true);
6026
+ return getPropertyTypeForIndexType(apparentObjectType , indexType, accessNode, /*cacheSymbol*/ true);
6055
6027
}
6056
6028
6057
6029
function getTypeFromIndexedAccessTypeNode(node: IndexedAccessTypeNode) {
@@ -7123,13 +7095,6 @@ namespace ts {
7123
7095
7124
7096
if (isSimpleTypeRelatedTo(source, target, relation, reportErrors ? reportError : undefined)) return Ternary.True;
7125
7097
7126
- if (source.flags & TypeFlags.Index) {
7127
- // A keyof T is related to a union type containing both string and number
7128
- if (maybeTypeOfKind(target, TypeFlags.String) && maybeTypeOfKind(target, TypeFlags.Number)) {
7129
- return Ternary.True;
7130
- }
7131
- }
7132
-
7133
7098
if (getObjectFlags(source) & ObjectFlags.ObjectLiteral && source.flags & TypeFlags.FreshLiteral) {
7134
7099
if (hasExcessProperties(<FreshObjectLiteralType>source, target, reportErrors)) {
7135
7100
if (reportErrors) {
@@ -10392,9 +10357,9 @@ namespace ts {
10392
10357
}
10393
10358
10394
10359
function getTypeForThisExpressionFromJSDoc(node: Node) {
10395
- const typeTag = getJSDocTypeTag (node);
10396
- if (typeTag && typeTag.typeExpression && typeTag.typeExpression.type && typeTag.typeExpression.type .kind === SyntaxKind.JSDocFunctionType) {
10397
- const jsDocFunctionType = <JSDocFunctionType>typeTag.typeExpression.type ;
10360
+ const jsdocType = getJSDocType (node);
10361
+ if (jsdocType && jsdocType .kind === SyntaxKind.JSDocFunctionType) {
10362
+ const jsDocFunctionType = <JSDocFunctionType>jsdocType ;
10398
10363
if (jsDocFunctionType.parameters.length > 0 && jsDocFunctionType.parameters[0].type.kind === SyntaxKind.JSDocThisType) {
10399
10364
return getTypeFromTypeNode(jsDocFunctionType.parameters[0].type);
10400
10365
}
@@ -13628,7 +13593,7 @@ namespace ts {
13628
13593
// the destructured type into the contained binding elements.
13629
13594
function assignBindingElementTypes(node: VariableLikeDeclaration) {
13630
13595
if (isBindingPattern(node.name)) {
13631
- for (const element of (<BindingPattern> node.name) .elements) {
13596
+ for (const element of node.name.elements) {
13632
13597
if (!isOmittedExpression(element)) {
13633
13598
if (element.name.kind === SyntaxKind.Identifier) {
13634
13599
getSymbolLinks(getSymbolOfNode(element)).type = getTypeForBindingElement(element);
@@ -14256,7 +14221,7 @@ namespace ts {
14256
14221
if (!isTypeAnyOrAllConstituentTypesHaveKind(leftType, TypeFlags.StringLike | TypeFlags.NumberLike | TypeFlags.ESSymbol)) {
14257
14222
error(left, Diagnostics.The_left_hand_side_of_an_in_expression_must_be_of_type_any_string_number_or_symbol);
14258
14223
}
14259
- if (!isTypeAnyOrAllConstituentTypesHaveKind(rightType, TypeFlags.Object | TypeFlags.TypeParameter)) {
14224
+ if (!isTypeAnyOrAllConstituentTypesHaveKind(rightType, TypeFlags.Object | TypeFlags.TypeParameter | TypeFlags.IndexedAccess )) {
14260
14225
error(right, Diagnostics.The_right_hand_side_of_an_in_expression_must_be_of_type_any_an_object_type_or_a_type_parameter);
14261
14226
}
14262
14227
return booleanType;
@@ -15650,7 +15615,7 @@ namespace ts {
15650
15615
const type = <MappedType>getTypeFromMappedTypeNode(node);
15651
15616
const constraintType = getConstraintTypeFromMappedType(type);
15652
15617
const keyType = constraintType.flags & TypeFlags.TypeParameter ? getApparentTypeOfTypeParameter(<TypeParameter>constraintType) : constraintType;
15653
- checkTypeAssignableTo(keyType, stringOrNumberType , node.typeParameter.constraint);
15618
+ checkTypeAssignableTo(keyType, stringType , node.typeParameter.constraint);
15654
15619
}
15655
15620
15656
15621
function isPrivateWithinAmbient(node: Node): boolean {
@@ -17161,7 +17126,7 @@ namespace ts {
17161
17126
const rightType = checkNonNullExpression(node.expression);
17162
17127
// unknownType is returned i.e. if node.expression is identifier whose name cannot be resolved
17163
17128
// in this case error about missing name is already reported - do not report extra one
17164
- if (!isTypeAnyOrAllConstituentTypesHaveKind(rightType, TypeFlags.Object | TypeFlags.TypeParameter)) {
17129
+ if (!isTypeAnyOrAllConstituentTypesHaveKind(rightType, TypeFlags.Object | TypeFlags.TypeParameter | TypeFlags.IndexedAccess )) {
17165
17130
error(node.expression, Diagnostics.The_right_hand_side_of_a_for_in_statement_must_be_of_type_any_an_object_type_or_a_type_parameter);
17166
17131
}
17167
17132
0 commit comments