@@ -309,6 +309,7 @@ import {
309
309
getJSDocDeprecatedTag,
310
310
getJSDocEnumTag,
311
311
getJSDocHost,
312
+ getJSDocOverloadTags,
312
313
getJSDocParameterTags,
313
314
getJSDocRoot,
314
315
getJSDocSatisfiesExpressionType,
@@ -602,6 +603,7 @@ import {
602
603
isJSDocSatisfiesTag,
603
604
isJSDocSignature,
604
605
isJSDocTemplateTag,
606
+ isJSDocThisTag,
605
607
isJSDocTypeAlias,
606
608
isJSDocTypeAssertion,
607
609
isJSDocTypedefTag,
@@ -970,6 +972,7 @@ import {
970
972
skipParentheses,
971
973
skipTrivia,
972
974
skipTypeChecking,
975
+ skipTypeParentheses,
973
976
some,
974
977
SourceFile,
975
978
SpreadAssignment,
@@ -2851,7 +2854,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
2851
2854
// still might be illegal if usage is in the initializer of the variable declaration (eg var a = a)
2852
2855
return !isImmediatelyUsedInInitializerOfBlockScopedVariable(declaration as VariableDeclaration, usage);
2853
2856
}
2854
- else if (isClassDeclaration (declaration)) {
2857
+ else if (isClassLike (declaration)) {
2855
2858
// still might be illegal if the usage is within a computed property name in the class (eg class A { static p = "a"; [A.p]() {} })
2856
2859
return !findAncestor(usage, n => isComputedPropertyName(n) && n.parent.parent === declaration);
2857
2860
}
@@ -8257,7 +8260,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
8257
8260
return factory.createStringLiteral(name, !!singleQuote);
8258
8261
}
8259
8262
if (isNumericLiteralName(name) && startsWith(name, "-")) {
8260
- return factory.createComputedPropertyName(factory.createNumericLiteral(+ name));
8263
+ return factory.createComputedPropertyName(factory.createPrefixUnaryExpression(SyntaxKind.MinusToken, factory. createNumericLiteral(- name) ));
8261
8264
}
8262
8265
return createPropertyNameNodeForIdentifierOrLiteral(name, getEmitScriptTarget(compilerOptions), singleQuote, stringNamed, isMethod);
8263
8266
}
@@ -12859,12 +12862,11 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
12859
12862
const baseTypes = getBaseTypes(source);
12860
12863
if (baseTypes.length) {
12861
12864
if (source.symbol && members === getMembersOfSymbol(source.symbol)) {
12862
- const symbolTable = createSymbolTable();
12863
- // copy all symbols (except type parameters), including the ones with internal names like `InternalSymbolName.Index`
12864
- for (const symbol of members.values()) {
12865
- if (!(symbol.flags & SymbolFlags.TypeParameter)) {
12866
- symbolTable.set(symbol.escapedName, symbol);
12867
- }
12865
+ const symbolTable = createSymbolTable(source.declaredProperties);
12866
+ // copy index signature symbol as well (for quickinfo)
12867
+ const sourceIndex = getIndexSymbol(source.symbol);
12868
+ if (sourceIndex) {
12869
+ symbolTable.set(InternalSymbolName.Index, sourceIndex);
12868
12870
}
12869
12871
members = symbolTable;
12870
12872
}
@@ -14880,6 +14882,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
14880
14882
let flags = SignatureFlags.None;
14881
14883
let minArgumentCount = 0;
14882
14884
let thisParameter: Symbol | undefined;
14885
+ let thisTag: JSDocThisTag | undefined = isInJSFile(declaration) ? getJSDocThisTag(declaration) : undefined;
14883
14886
let hasThisParameter = false;
14884
14887
const iife = getImmediatelyInvokedFunctionExpression(declaration);
14885
14888
const isJSConstructSignature = isJSDocConstructSignature(declaration);
@@ -14897,6 +14900,10 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
14897
14900
// signature.
14898
14901
for (let i = isJSConstructSignature ? 1 : 0; i < declaration.parameters.length; i++) {
14899
14902
const param = declaration.parameters[i];
14903
+ if (isInJSFile(param) && isJSDocThisTag(param)) {
14904
+ thisTag = param;
14905
+ continue;
14906
+ }
14900
14907
14901
14908
let paramSymbol = param.symbol;
14902
14909
const type = isJSDocParameterTag(param) ? (param.typeExpression && param.typeExpression.type) : param.type;
@@ -14940,11 +14947,8 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
14940
14947
}
14941
14948
}
14942
14949
14943
- if (isInJSFile(declaration)) {
14944
- const thisTag = getJSDocThisTag(declaration);
14945
- if (thisTag && thisTag.typeExpression) {
14946
- thisParameter = createSymbolWithType(createSymbol(SymbolFlags.FunctionScopedVariable, InternalSymbolName.This), getTypeFromTypeNode(thisTag.typeExpression));
14947
- }
14950
+ if (thisTag && thisTag.typeExpression) {
14951
+ thisParameter = createSymbolWithType(createSymbol(SymbolFlags.FunctionScopedVariable, InternalSymbolName.This), getTypeFromTypeNode(thisTag.typeExpression));
14948
14952
}
14949
14953
14950
14954
const hostDeclaration = isJSDocSignature(declaration) ? getEffectiveJSDocHost(declaration) : declaration;
@@ -15075,22 +15079,15 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
15075
15079
}
15076
15080
}
15077
15081
if (isInJSFile(decl) && decl.jsDoc) {
15078
- let hasJSDocOverloads = false;
15079
- for (const node of decl.jsDoc) {
15080
- if (node.tags) {
15081
- for (const tag of node.tags) {
15082
- if (isJSDocOverloadTag(tag)) {
15083
- const jsDocSignature = tag.typeExpression;
15084
- if (jsDocSignature.type === undefined && !isConstructorDeclaration(decl)) {
15085
- reportImplicitAny(jsDocSignature, anyType);
15086
- }
15087
- result.push(getSignatureFromDeclaration(jsDocSignature));
15088
- hasJSDocOverloads = true;
15089
- }
15082
+ const tags = getJSDocOverloadTags(decl);
15083
+ if (length(tags)) {
15084
+ for (const tag of tags) {
15085
+ const jsDocSignature = tag.typeExpression;
15086
+ if (jsDocSignature.type === undefined && !isConstructorDeclaration(decl)) {
15087
+ reportImplicitAny(jsDocSignature, anyType);
15090
15088
}
15089
+ result.push(getSignatureFromDeclaration(jsDocSignature));
15091
15090
}
15092
- }
15093
- if (hasJSDocOverloads) {
15094
15091
continue;
15095
15092
}
15096
15093
}
@@ -18295,7 +18292,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
18295
18292
return constraint && (isGenericObjectType(constraint) || isGenericIndexType(constraint)) ? cloneTypeParameter(p) : p;
18296
18293
}
18297
18294
18298
- function isSimpleTupleType(node: TypeNode) {
18295
+ function isSimpleTupleType(node: TypeNode): boolean {
18299
18296
return isTupleTypeNode(node) && length(node.elements) > 0 &&
18300
18297
!some(node.elements, e => isOptionalTypeNode(e) || isRestTypeNode(e) || isNamedTupleMember(e) && !!(e.questionToken || e.dotDotDotToken));
18301
18298
}
@@ -18326,11 +18323,13 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
18326
18323
if (checkType === wildcardType || extendsType === wildcardType) {
18327
18324
return wildcardType;
18328
18325
}
18326
+ const checkTypeNode = skipTypeParentheses(root.node.checkType);
18327
+ const extendsTypeNode = skipTypeParentheses(root.node.extendsType);
18329
18328
// When the check and extends types are simple tuple types of the same arity, we defer resolution of the
18330
18329
// conditional type when any tuple elements are generic. This is such that non-distributable conditional
18331
18330
// types can be written `[X] extends [Y] ? ...` and be deferred similarly to `X extends Y ? ...`.
18332
- const checkTuples = isSimpleTupleType(root.node.checkType ) && isSimpleTupleType(root.node.extendsType ) &&
18333
- length((root.node.checkType as TupleTypeNode).elements) === length((root.node.extendsType as TupleTypeNode).elements);
18331
+ const checkTuples = isSimpleTupleType(checkTypeNode ) && isSimpleTupleType(extendsTypeNode ) &&
18332
+ length((checkTypeNode as TupleTypeNode).elements) === length((extendsTypeNode as TupleTypeNode).elements);
18334
18333
const checkTypeDeferred = isDeferredType(checkType, checkTuples);
18335
18334
let combinedMapper: TypeMapper | undefined;
18336
18335
if (root.inferTypeParameters) {
@@ -20492,8 +20491,8 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
20492
20491
// similar to return values, callback parameters are output positions. This means that a Promise<T>,
20493
20492
// where T is used only in callback parameter positions, will be co-variant (as opposed to bi-variant)
20494
20493
// with respect to T.
20495
- const sourceSig = checkMode & SignatureCheckMode.Callback ? undefined : getSingleCallSignature(getNonNullableType(sourceType));
20496
- const targetSig = checkMode & SignatureCheckMode.Callback ? undefined : getSingleCallSignature(getNonNullableType(targetType));
20494
+ const sourceSig = checkMode & SignatureCheckMode.Callback || isInstantiatedGenericParameter(source, i) ? undefined : getSingleCallSignature(getNonNullableType(sourceType));
20495
+ const targetSig = checkMode & SignatureCheckMode.Callback || isInstantiatedGenericParameter(target, i) ? undefined : getSingleCallSignature(getNonNullableType(targetType));
20497
20496
const callbacks = sourceSig && targetSig && !getTypePredicateOfSignature(sourceSig) && !getTypePredicateOfSignature(targetSig) &&
20498
20497
getTypeFacts(sourceType, TypeFacts.IsUndefinedOrNull) === getTypeFacts(targetType, TypeFacts.IsUndefinedOrNull);
20499
20498
let related = callbacks ?
@@ -25155,7 +25154,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
25155
25154
target = getIntersectionType(targets);
25156
25155
}
25157
25156
}
25158
- else if (target.flags & (TypeFlags.IndexedAccess | TypeFlags.Substitution)) {
25157
+ if (target.flags & (TypeFlags.IndexedAccess | TypeFlags.Substitution)) {
25159
25158
target = getActualTypeVariable(target);
25160
25159
}
25161
25160
if (target.flags & TypeFlags.TypeVariable) {
@@ -33287,6 +33286,11 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
33287
33286
(typeArguments.length >= minTypeArgumentCount && typeArguments.length <= numTypeParameters);
33288
33287
}
33289
33288
33289
+ function isInstantiatedGenericParameter(signature: Signature, pos: number) {
33290
+ let type;
33291
+ return !!(signature.target && (type = tryGetTypeAtPosition(signature.target, pos)) && isGenericType(type));
33292
+ }
33293
+
33290
33294
// If type has a single call signature and no other members, return that signature. Otherwise, return undefined.
33291
33295
function getSingleCallSignature(type: Type): Signature | undefined {
33292
33296
return getSingleSignature(type, SignatureKind.Call, /*allowMembers*/ false);
@@ -36014,9 +36018,16 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
36014
36018
const len = signature.parameters.length - (signatureHasRestParameter(signature) ? 1 : 0);
36015
36019
for (let i = 0; i < len; i++) {
36016
36020
const parameter = signature.parameters[i];
36017
- if (!getEffectiveTypeAnnotationNode(parameter.valueDeclaration as ParameterDeclaration)) {
36018
- const contextualParameterType = tryGetTypeAtPosition(context, i);
36019
- assignParameterType(parameter, contextualParameterType);
36021
+ const declaration = parameter.valueDeclaration as ParameterDeclaration;
36022
+ if (!getEffectiveTypeAnnotationNode(declaration)) {
36023
+ let type = tryGetTypeAtPosition(context, i);
36024
+ if (type && declaration.initializer) {
36025
+ let initializerType = checkDeclarationInitializer(declaration, CheckMode.Normal);
36026
+ if (!isTypeAssignableTo(initializerType, type) && isTypeAssignableTo(type, initializerType = widenTypeInferredFromInitializer(declaration, initializerType))) {
36027
+ type = initializerType;
36028
+ }
36029
+ }
36030
+ assignParameterType(parameter, type);
36020
36031
}
36021
36032
}
36022
36033
if (signatureHasRestParameter(signature)) {
@@ -40300,15 +40311,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
40300
40311
}
40301
40312
}
40302
40313
if (isInJSFile(current) && isFunctionLike(current) && current.jsDoc) {
40303
- for (const node of current.jsDoc) {
40304
- if (node.tags) {
40305
- for (const tag of node.tags) {
40306
- if (isJSDocOverloadTag(tag)) {
40307
- hasOverloads = true;
40308
- }
40309
- }
40310
- }
40311
- }
40314
+ hasOverloads = length(getJSDocOverloadTags(current)) > 0;
40312
40315
}
40313
40316
}
40314
40317
}
@@ -44822,7 +44825,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
44822
44825
}
44823
44826
else {
44824
44827
const text = getTextOfPropertyName(member.name);
44825
- if (isNumericLiteralName(text) && !isInfinityOrNaNString(text) ) {
44828
+ if (isNumericLiteralName(text)) {
44826
44829
error(member.name, Diagnostics.An_enum_member_cannot_have_a_numeric_name);
44827
44830
}
44828
44831
}
@@ -47922,8 +47925,9 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
47922
47925
if (enumResult) return enumResult;
47923
47926
const literalValue = (type as LiteralType).value;
47924
47927
return typeof literalValue === "object" ? factory.createBigIntLiteral(literalValue) :
47925
- typeof literalValue === "number" ? factory.createNumericLiteral(literalValue) :
47926
- factory.createStringLiteral(literalValue);
47928
+ typeof literalValue === "string" ? factory.createStringLiteral(literalValue) :
47929
+ literalValue < 0 ? factory.createPrefixUnaryExpression(SyntaxKind.MinusToken, factory.createNumericLiteral(-literalValue)) :
47930
+ factory.createNumericLiteral(literalValue);
47927
47931
}
47928
47932
47929
47933
function createLiteralConstValue(node: VariableDeclaration | PropertyDeclaration | PropertySignature | ParameterDeclaration, tracker: SymbolTracker) {
0 commit comments