From 762fff1f65d990aaf79202aaaa02e4a5d7ae7b83 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Sun, 23 Jun 2019 09:00:42 -1000 Subject: [PATCH 01/10] Remove duplicate call/construct signatures in intersections --- src/compiler/checker.ts | 19 ++++++++++++++----- 1 file changed, 14 insertions(+), 5 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 9cb08b3e440..414d815d5d2 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -7234,8 +7234,8 @@ namespace ts { function resolveIntersectionTypeMembers(type: IntersectionType) { // The members and properties collections are empty for intersection types. To get all properties of an // intersection type use getPropertiesOfType (only the language service uses this). - let callSignatures: ReadonlyArray = emptyArray; - let constructSignatures: ReadonlyArray = emptyArray; + let callSignatures: Signature[] | undefined; + let constructSignatures: Signature[] | undefined; let stringIndexInfo: IndexInfo | undefined; let numberIndexInfo: IndexInfo | undefined; const types = type.types; @@ -7257,13 +7257,22 @@ namespace ts { return clone; }); } - constructSignatures = concatenate(constructSignatures, signatures); + constructSignatures = appendSignatures(constructSignatures, signatures); } - callSignatures = concatenate(callSignatures, getSignaturesOfType(t, SignatureKind.Call)); + callSignatures = appendSignatures(callSignatures, getSignaturesOfType(t, SignatureKind.Call)); stringIndexInfo = intersectIndexInfos(stringIndexInfo, getIndexInfoOfType(t, IndexKind.String)); numberIndexInfo = intersectIndexInfos(numberIndexInfo, getIndexInfoOfType(t, IndexKind.Number)); } - setStructuredTypeMembers(type, emptySymbols, callSignatures, constructSignatures, stringIndexInfo, numberIndexInfo); + setStructuredTypeMembers(type, emptySymbols, callSignatures || emptyArray, constructSignatures || emptyArray, stringIndexInfo, numberIndexInfo); + } + + function appendSignatures(signatures: Signature[] | undefined, newSignatures: readonly Signature[]) { + for (const sig of newSignatures) { + if (!signatures || every(signatures, s => !compareSignaturesIdentical(s, sig, /*partialMatch*/ false, /*ignoreThisTypes*/ false, /*ignoreReturnTypes*/ false, compareTypesIdentical))) { + signatures = append(signatures, sig); + } + } + return signatures; } /** From 076d9ad2ab208ae57d59c6ad17654dcaac375b0d Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Sun, 23 Jun 2019 09:19:56 -1000 Subject: [PATCH 02/10] Add regression test --- .../conformance/types/keyof/keyofAndIndexedAccess2.ts | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/tests/cases/conformance/types/keyof/keyofAndIndexedAccess2.ts b/tests/cases/conformance/types/keyof/keyofAndIndexedAccess2.ts index b242aa3de60..a86f4718e35 100644 --- a/tests/cases/conformance/types/keyof/keyofAndIndexedAccess2.ts +++ b/tests/cases/conformance/types/keyof/keyofAndIndexedAccess2.ts @@ -158,3 +158,12 @@ type Bar = { [key: string]: { [K in keyof T]: [K] }[keyof T] }; type Baz> = { [K in keyof Q]: T[Q[K]] }; type Qux> = { [K in keyof Q]: T[Q[K]["0"]] }; + +// Repro from #32038 + +const actions = ['resizeTo', 'resizeBy'] as const; +for (const action of actions) { + window[action] = (x, y) => { + window[action](x, y); + } +} From be4147ddf33810f304fd97cc6e398bee12ba9350 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Sun, 23 Jun 2019 09:20:03 -1000 Subject: [PATCH 03/10] Accept new baselines --- .../keyofAndIndexedAccess2.errors.txt | 9 ++++++ .../reference/keyofAndIndexedAccess2.js | 16 ++++++++++ .../reference/keyofAndIndexedAccess2.symbols | 23 +++++++++++++ .../reference/keyofAndIndexedAccess2.types | 32 +++++++++++++++++++ 4 files changed, 80 insertions(+) diff --git a/tests/baselines/reference/keyofAndIndexedAccess2.errors.txt b/tests/baselines/reference/keyofAndIndexedAccess2.errors.txt index ff96efe3e13..b00409544de 100644 --- a/tests/baselines/reference/keyofAndIndexedAccess2.errors.txt +++ b/tests/baselines/reference/keyofAndIndexedAccess2.errors.txt @@ -237,4 +237,13 @@ tests/cases/conformance/types/keyof/keyofAndIndexedAccess2.ts(108,5): error TS23 type Baz> = { [K in keyof Q]: T[Q[K]] }; type Qux> = { [K in keyof Q]: T[Q[K]["0"]] }; + + // Repro from #32038 + + const actions = ['resizeTo', 'resizeBy'] as const; + for (const action of actions) { + window[action] = (x, y) => { + window[action](x, y); + } + } \ No newline at end of file diff --git a/tests/baselines/reference/keyofAndIndexedAccess2.js b/tests/baselines/reference/keyofAndIndexedAccess2.js index 91cf2c89ff2..a2d7f9b2fdd 100644 --- a/tests/baselines/reference/keyofAndIndexedAccess2.js +++ b/tests/baselines/reference/keyofAndIndexedAccess2.js @@ -156,6 +156,15 @@ type Bar = { [key: string]: { [K in keyof T]: [K] }[keyof T] }; type Baz> = { [K in keyof Q]: T[Q[K]] }; type Qux> = { [K in keyof Q]: T[Q[K]["0"]] }; + +// Repro from #32038 + +const actions = ['resizeTo', 'resizeBy'] as const; +for (const action of actions) { + window[action] = (x, y) => { + window[action](x, y); + } +} //// [keyofAndIndexedAccess2.js] @@ -253,3 +262,10 @@ export class c { this["a"] = "b"; } } +// Repro from #32038 +const actions = ['resizeTo', 'resizeBy']; +for (const action of actions) { + window[action] = (x, y) => { + window[action](x, y); + }; +} diff --git a/tests/baselines/reference/keyofAndIndexedAccess2.symbols b/tests/baselines/reference/keyofAndIndexedAccess2.symbols index 4a7721ff801..58b5f470c03 100644 --- a/tests/baselines/reference/keyofAndIndexedAccess2.symbols +++ b/tests/baselines/reference/keyofAndIndexedAccess2.symbols @@ -564,3 +564,26 @@ type Qux> = { [K in keyof Q]: T[Q[K]["0"]] }; >Q : Symbol(Q, Decl(keyofAndIndexedAccess2.ts, 156, 11)) >K : Symbol(K, Decl(keyofAndIndexedAccess2.ts, 156, 35)) +// Repro from #32038 + +const actions = ['resizeTo', 'resizeBy'] as const; +>actions : Symbol(actions, Decl(keyofAndIndexedAccess2.ts, 160, 5)) + +for (const action of actions) { +>action : Symbol(action, Decl(keyofAndIndexedAccess2.ts, 161, 10)) +>actions : Symbol(actions, Decl(keyofAndIndexedAccess2.ts, 160, 5)) + + window[action] = (x, y) => { +>window : Symbol(window, Decl(lib.dom.d.ts, --, --)) +>action : Symbol(action, Decl(keyofAndIndexedAccess2.ts, 161, 10)) +>x : Symbol(x, Decl(keyofAndIndexedAccess2.ts, 162, 19)) +>y : Symbol(y, Decl(keyofAndIndexedAccess2.ts, 162, 21)) + + window[action](x, y); +>window : Symbol(window, Decl(lib.dom.d.ts, --, --)) +>action : Symbol(action, Decl(keyofAndIndexedAccess2.ts, 161, 10)) +>x : Symbol(x, Decl(keyofAndIndexedAccess2.ts, 162, 19)) +>y : Symbol(y, Decl(keyofAndIndexedAccess2.ts, 162, 21)) + } +} + diff --git a/tests/baselines/reference/keyofAndIndexedAccess2.types b/tests/baselines/reference/keyofAndIndexedAccess2.types index b282588cc51..5824619c6ee 100644 --- a/tests/baselines/reference/keyofAndIndexedAccess2.types +++ b/tests/baselines/reference/keyofAndIndexedAccess2.types @@ -540,3 +540,35 @@ type Baz> = { [K in keyof Q]: T[Q[K]] }; type Qux> = { [K in keyof Q]: T[Q[K]["0"]] }; >Qux : Qux +// Repro from #32038 + +const actions = ['resizeTo', 'resizeBy'] as const; +>actions : readonly ["resizeTo", "resizeBy"] +>['resizeTo', 'resizeBy'] as const : readonly ["resizeTo", "resizeBy"] +>['resizeTo', 'resizeBy'] : readonly ["resizeTo", "resizeBy"] +>'resizeTo' : "resizeTo" +>'resizeBy' : "resizeBy" + +for (const action of actions) { +>action : "resizeTo" | "resizeBy" +>actions : readonly ["resizeTo", "resizeBy"] + + window[action] = (x, y) => { +>window[action] = (x, y) => { window[action](x, y); } : (x: number, y: number) => void +>window[action] : ((x: number, y: number) => void) & ((x: number, y: number) => void) +>window : Window +>action : "resizeTo" | "resizeBy" +>(x, y) => { window[action](x, y); } : (x: number, y: number) => void +>x : number +>y : number + + window[action](x, y); +>window[action](x, y) : void +>window[action] : ((x: number, y: number) => void) | ((x: number, y: number) => void) +>window : Window +>action : "resizeTo" | "resizeBy" +>x : number +>y : number + } +} + From 314f2e68b75328fdea4604552900f30c7357f7ca Mon Sep 17 00:00:00 2001 From: Sasha Joseph Date: Mon, 24 Jun 2019 17:05:19 -0700 Subject: [PATCH 04/10] Make close() in interface Watch public Closes #31526 --- src/compiler/watch.ts | 1 - tests/baselines/reference/api/tsserverlibrary.d.ts | 2 ++ tests/baselines/reference/api/typescript.d.ts | 2 ++ 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/src/compiler/watch.ts b/src/compiler/watch.ts index 3ba2a5f5959..aa47c0bf91e 100644 --- a/src/compiler/watch.ts +++ b/src/compiler/watch.ts @@ -603,7 +603,6 @@ namespace ts { /*@internal*/ getCurrentProgram(): T; /** Closes the watch */ - /*@internal*/ close(): void; } diff --git a/tests/baselines/reference/api/tsserverlibrary.d.ts b/tests/baselines/reference/api/tsserverlibrary.d.ts index 82ab70b6e6f..ab1e0ab2170 100644 --- a/tests/baselines/reference/api/tsserverlibrary.d.ts +++ b/tests/baselines/reference/api/tsserverlibrary.d.ts @@ -4548,6 +4548,8 @@ declare namespace ts { interface Watch { /** Synchronize with host and get updated program */ getProgram(): T; + /** Closes the watch */ + close(): void; } /** * Creates the watch what generates program using the config file diff --git a/tests/baselines/reference/api/typescript.d.ts b/tests/baselines/reference/api/typescript.d.ts index 0c55cff1275..92cca502a61 100644 --- a/tests/baselines/reference/api/typescript.d.ts +++ b/tests/baselines/reference/api/typescript.d.ts @@ -4548,6 +4548,8 @@ declare namespace ts { interface Watch { /** Synchronize with host and get updated program */ getProgram(): T; + /** Closes the watch */ + close(): void; } /** * Creates the watch what generates program using the config file From ea0a6de82fa0bb4c4ee07a53233d6eabc506c413 Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 26 Jun 2019 18:09:30 -1000 Subject: [PATCH 05/10] Compare type parameters, constraints, and defaults in signature identity --- src/compiler/checker.ts | 26 +++++++++++++++----------- 1 file changed, 15 insertions(+), 11 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 414d815d5d2..41520ea8992 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -14322,20 +14322,25 @@ namespace ts { if (!(isMatchingSignature(source, target, partialMatch))) { return Ternary.False; } - // Check that the two signatures have the same number of type parameters. We might consider - // also checking that any type parameter constraints match, but that would require instantiating - // the constraints with a common set of type arguments to get relatable entities in places where - // type parameters occur in the constraints. The complexity of doing that doesn't seem worthwhile, - // particularly as we're comparing erased versions of the signatures below. + // Check that the two signatures have the same number of type parameters. if (length(source.typeParameters) !== length(target.typeParameters)) { return Ternary.False; } - // Spec 1.0 Section 3.8.3 & 3.8.4: - // M and N (the signatures) are instantiated using type Any as the type argument for all type parameters declared by M and N - source = getErasedSignature(source); - target = getErasedSignature(target); + // Check that type parameter constraints and defaults match. If they do, instantiate the source + // signature with the type parameters of the target signature and continue the comparison. + if (target.typeParameters) { + const mapper = createTypeMapper(source.typeParameters!, target.typeParameters); + for (let i = 0; i < target.typeParameters.length; i++) { + const s = source.typeParameters![i]; + const t = target.typeParameters[i]; + if (!(s === t || compareTypes(instantiateType(getConstraintFromTypeParameter(s), mapper) || unknownType, getConstraintFromTypeParameter(t) || unknownType) && + compareTypes(instantiateType(getDefaultFromTypeParameter(s), mapper) || unknownType, getDefaultFromTypeParameter(t) || unknownType))) { + return Ternary.False; + } + } + source = instantiateSignature(source, mapper, /*eraseTypeParameters*/ true); + } let result = Ternary.True; - if (!ignoreThisTypes) { const sourceThisType = getThisTypeOfSignature(source); if (sourceThisType) { @@ -14349,7 +14354,6 @@ namespace ts { } } } - const targetLen = getParameterCount(target); for (let i = 0; i < targetLen; i++) { const s = getTypeAtPosition(source, i); From 10c9fbc357a98c33bf04653d5086b540f243a2fa Mon Sep 17 00:00:00 2001 From: Anders Hejlsberg Date: Wed, 26 Jun 2019 18:11:03 -1000 Subject: [PATCH 06/10] Accept new baselines --- .../genericSignatureIdentity.errors.txt | 36 +++++++++++++++++++ ...naturesWithTypeParametersAndAny.errors.txt | 6 +++- ...turesWithTypeParametersSwitched.errors.txt | 9 +++++ .../reference/promiseIdentity.errors.txt | 28 +++++++++++++++ .../promiseIdentityWithAny.errors.txt | 17 +++++++++ .../promiseIdentityWithConstraints.errors.txt | 17 +++++++++ 6 files changed, 112 insertions(+), 1 deletion(-) create mode 100644 tests/baselines/reference/genericSignatureIdentity.errors.txt create mode 100644 tests/baselines/reference/identityForSignaturesWithTypeParametersSwitched.errors.txt create mode 100644 tests/baselines/reference/promiseIdentity.errors.txt create mode 100644 tests/baselines/reference/promiseIdentityWithAny.errors.txt create mode 100644 tests/baselines/reference/promiseIdentityWithConstraints.errors.txt diff --git a/tests/baselines/reference/genericSignatureIdentity.errors.txt b/tests/baselines/reference/genericSignatureIdentity.errors.txt new file mode 100644 index 00000000000..6aed55a1237 --- /dev/null +++ b/tests/baselines/reference/genericSignatureIdentity.errors.txt @@ -0,0 +1,36 @@ +tests/cases/compiler/genericSignatureIdentity.ts(10,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: T) => T'. +tests/cases/compiler/genericSignatureIdentity.ts(14,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: T) => T'. +tests/cases/compiler/genericSignatureIdentity.ts(18,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: any) => any'. + + +==== tests/cases/compiler/genericSignatureIdentity.ts (3 errors) ==== + // This test is here to remind us of our current limits of type identity checking. + // Ideally all of the below declarations would be considered different (and thus errors) + // but they aren't because we erase type parameters to type any and don't check that + // constraints are identical. + + var x: { + (x: T): T; + }; + + var x: { + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: T) => T'. +!!! related TS6203 tests/cases/compiler/genericSignatureIdentity.ts:6:5: 'x' was also declared here. + (x: T): T; + }; + + var x: { + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: T) => T'. +!!! related TS6203 tests/cases/compiler/genericSignatureIdentity.ts:6:5: 'x' was also declared here. + (x: T): T; + }; + + var x: { + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type '(x: T) => T', but here has type '(x: any) => any'. +!!! related TS6203 tests/cases/compiler/genericSignatureIdentity.ts:6:5: 'x' was also declared here. + (x: any): any; + }; + \ No newline at end of file diff --git a/tests/baselines/reference/identityForSignaturesWithTypeParametersAndAny.errors.txt b/tests/baselines/reference/identityForSignaturesWithTypeParametersAndAny.errors.txt index 092bfaaeeb3..11fb2950aa8 100644 --- a/tests/baselines/reference/identityForSignaturesWithTypeParametersAndAny.errors.txt +++ b/tests/baselines/reference/identityForSignaturesWithTypeParametersAndAny.errors.txt @@ -1,12 +1,16 @@ +tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts(2,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'f' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: any) => any'. tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts(5,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'g' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: any) => any'. tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts(8,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'h' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: any) => any'. tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts(11,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'i' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: string) => any'. tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts(14,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'j' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: any) => string'. -==== tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts (4 errors) ==== +==== tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts (5 errors) ==== var f: (x: T, y: U) => T; var f: (x: any, y: any) => any; + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'f' must be of type '(x: T, y: U) => T', but here has type '(x: any, y: any) => any'. +!!! related TS6203 tests/cases/compiler/identityForSignaturesWithTypeParametersAndAny.ts:1:5: 'f' was also declared here. var g: (x: T, y: U) => T; var g: (x: any, y: any) => any; diff --git a/tests/baselines/reference/identityForSignaturesWithTypeParametersSwitched.errors.txt b/tests/baselines/reference/identityForSignaturesWithTypeParametersSwitched.errors.txt new file mode 100644 index 00000000000..81d0eb6c961 --- /dev/null +++ b/tests/baselines/reference/identityForSignaturesWithTypeParametersSwitched.errors.txt @@ -0,0 +1,9 @@ +tests/cases/compiler/identityForSignaturesWithTypeParametersSwitched.ts(2,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'f' must be of type '(x: T, y: U) => T', but here has type '(x: U, y: T) => U'. + + +==== tests/cases/compiler/identityForSignaturesWithTypeParametersSwitched.ts (1 errors) ==== + var f: (x: T, y: U) => T; + var f: (x: U, y: T) => U; + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'f' must be of type '(x: T, y: U) => T', but here has type '(x: U, y: T) => U'. +!!! related TS6203 tests/cases/compiler/identityForSignaturesWithTypeParametersSwitched.ts:1:5: 'f' was also declared here. \ No newline at end of file diff --git a/tests/baselines/reference/promiseIdentity.errors.txt b/tests/baselines/reference/promiseIdentity.errors.txt new file mode 100644 index 00000000000..b104dc68e5f --- /dev/null +++ b/tests/baselines/reference/promiseIdentity.errors.txt @@ -0,0 +1,28 @@ +tests/cases/compiler/promiseIdentity.ts(21,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'y' must be of type 'IPromise2', but here has type 'Promise2'. + + +==== tests/cases/compiler/promiseIdentity.ts (1 errors) ==== + export interface IPromise { + then(callback: (x: T) => IPromise): IPromise; + } + interface Promise { + then(callback: (x: T) => Promise): Promise; + } + var x: IPromise; + var x: Promise; + + + interface IPromise2 { + then(callback: (x: T) => IPromise2): IPromise2; + } + interface Promise2 { + then(callback: (x: V) => Promise2): Promise2; // Uses V instead of T in callback's parameter + } + + // Ok because T in this particular Promise2 is any, as are all the U and W references. + // Also, the V of Promise2 happens to coincide with the T of IPromise2 (they are both string). + var y: IPromise2; + var y: Promise2; + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'y' must be of type 'IPromise2', but here has type 'Promise2'. +!!! related TS6203 tests/cases/compiler/promiseIdentity.ts:20:5: 'y' was also declared here. \ No newline at end of file diff --git a/tests/baselines/reference/promiseIdentityWithAny.errors.txt b/tests/baselines/reference/promiseIdentityWithAny.errors.txt new file mode 100644 index 00000000000..c318925c617 --- /dev/null +++ b/tests/baselines/reference/promiseIdentityWithAny.errors.txt @@ -0,0 +1,17 @@ +tests/cases/compiler/promiseIdentityWithAny.ts(10,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type 'IPromise', but here has type 'Promise'. + + +==== tests/cases/compiler/promiseIdentityWithAny.ts (1 errors) ==== + export interface IPromise { + then(callback: (x: T) => IPromise): IPromise; + } + export interface Promise { + then(callback: (x: T) => Promise): Promise; + } + + // Should be ok because signature type parameters get erased to any + var x: IPromise; + var x: Promise; + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type 'IPromise', but here has type 'Promise'. +!!! related TS6203 tests/cases/compiler/promiseIdentityWithAny.ts:9:5: 'x' was also declared here. \ No newline at end of file diff --git a/tests/baselines/reference/promiseIdentityWithConstraints.errors.txt b/tests/baselines/reference/promiseIdentityWithConstraints.errors.txt new file mode 100644 index 00000000000..9b72f8363ed --- /dev/null +++ b/tests/baselines/reference/promiseIdentityWithConstraints.errors.txt @@ -0,0 +1,17 @@ +tests/cases/compiler/promiseIdentityWithConstraints.ts(10,5): error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type 'IPromise', but here has type 'Promise'. + + +==== tests/cases/compiler/promiseIdentityWithConstraints.ts (1 errors) ==== + export interface IPromise { + then(callback: (x: T) => IPromise): IPromise; + } + export interface Promise { + then(callback: (x: T) => Promise): Promise; + } + + // Error because constraint V doesn't match + var x: IPromise; + var x: Promise; + ~ +!!! error TS2403: Subsequent variable declarations must have the same type. Variable 'x' must be of type 'IPromise', but here has type 'Promise'. +!!! related TS6203 tests/cases/compiler/promiseIdentityWithConstraints.ts:9:5: 'x' was also declared here. \ No newline at end of file From 4195f1a409c63940cf20724b806c0997f3a7339f Mon Sep 17 00:00:00 2001 From: Austin Cummings Date: Wed, 26 Jun 2019 17:30:44 -0700 Subject: [PATCH 07/10] Add affectsEmit to module and esModuleInterop options --- src/compiler/commandLineParser.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/compiler/commandLineParser.ts b/src/compiler/commandLineParser.ts index eb12242a84f..4747b89f08c 100644 --- a/src/compiler/commandLineParser.ts +++ b/src/compiler/commandLineParser.ts @@ -245,6 +245,7 @@ namespace ts { esnext: ModuleKind.ESNext }), affectsModuleResolution: true, + affectsEmit: true, paramType: Diagnostics.KIND, showInSimplifiedHelpView: true, category: Diagnostics.Basic_Options, @@ -590,6 +591,7 @@ namespace ts { name: "esModuleInterop", type: "boolean", affectsSemanticDiagnostics: true, + affectsEmit: true, showInSimplifiedHelpView: true, category: Diagnostics.Module_Resolution_Options, description: Diagnostics.Enables_emit_interoperability_between_CommonJS_and_ES_Modules_via_creation_of_namespace_objects_for_all_imports_Implies_allowSyntheticDefaultImports From 5b694f83022bc9d817d92737503ea7f7248c526f Mon Sep 17 00:00:00 2001 From: Austin Cummings Date: Fri, 28 Jun 2019 18:34:59 -0700 Subject: [PATCH 08/10] Add tests for module and esModuleInterop affectsEmit change --- src/testRunner/unittests/tsbuild/sample.ts | 84 +++++++++++++- .../when-esModuleInterop-option-changes.js | 107 +++++++++++++++++ .../when-module-option-changes.js | 66 +++++++++++ .../when-esModuleInterop-option-changes.js | 109 ++++++++++++++++++ .../when-module-option-changes.js | 62 ++++++++++ 5 files changed, 427 insertions(+), 1 deletion(-) create mode 100644 tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js create mode 100644 tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-module-option-changes.js create mode 100644 tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js create mode 100644 tests/baselines/reference/tsbuild/sample1/initial-Build/when-module-option-changes.js diff --git a/src/testRunner/unittests/tsbuild/sample.ts b/src/testRunner/unittests/tsbuild/sample.ts index df2fb62db25..a75cc9e8765 100644 --- a/src/testRunner/unittests/tsbuild/sample.ts +++ b/src/testRunner/unittests/tsbuild/sample.ts @@ -906,7 +906,7 @@ class someClass { }`), "target": "esnext", } }`); - }, + }, expectedDiagnostics: [ getExpectedDiagnosticForProjectsInBuild("src/core/tsconfig.json"), [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/core/tsconfig.json", "src/core/anotherModule.js"], @@ -931,6 +931,88 @@ class someClass { }`), baselineOnly: true, verifyDiagnostics: true }); + + verifyTsbuildOutput({ + scenario: "when module option changes", + projFs: () => projFs, + time, + tick, + proj: "sample1", + rootNames: ["/src/core"], + expectedMapFileNames: emptyArray, + lastProjectOutputJs: "/src/core/index.js", + initialBuild: { + modifyFs: fs => fs.writeFileSync("/src/core/tsconfig.json", `{ + "compilerOptions": { + "incremental": true, + "module": "commonjs" + } +}`), + expectedDiagnostics: [ + getExpectedDiagnosticForProjectsInBuild("src/core/tsconfig.json"), + [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/core/tsconfig.json", "src/core/anotherModule.js"], + [Diagnostics.Building_project_0, "/src/core/tsconfig.json"], + ] + }, + incrementalDtsChangedBuild: { + modifyFs: fs => replaceText(fs, "/src/core/tsconfig.json", `"module": "commonjs"`, `"module": "amd"`), + expectedDiagnostics: [ + getExpectedDiagnosticForProjectsInBuild("src/core/tsconfig.json"), + [Diagnostics.Project_0_is_out_of_date_because_oldest_output_1_is_older_than_newest_input_2, "src/core/tsconfig.json", "src/core/anotherModule.js", "src/core/tsconfig.json"], + [Diagnostics.Building_project_0, "/src/core/tsconfig.json"] + ] + }, + outputFiles: [ + "/src/core/anotherModule.js", + "/src/core/index.js", + "/src/core/tsconfig.tsbuildinfo", + ], + baselineOnly: true, + verifyDiagnostics: true + }); + + verifyTsbuildOutput({ + scenario: "when esModuleInterop option changes", + projFs: () => projFs, + time, + tick, + proj: "sample1", + rootNames: ["/src/tests"], + expectedMapFileNames: emptyArray, + lastProjectOutputJs: "/src/tests/index.js", + initialBuild: { + modifyFs: fs => fs.writeFileSync("/src/tests/tsconfig.json", `{ + "compilerOptions": { + "incremental": true, + "module": "commonjs", + "esModuleInterop": false + } +}`), + expectedDiagnostics: [ + getExpectedDiagnosticForProjectsInBuild("src/tests/tsconfig.json"), + [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/tests/tsconfig.json", "src/tests/index.js"], + [Diagnostics.Building_project_0, "/src/tests/tsconfig.json"], + ] + }, + incrementalDtsChangedBuild: { + modifyFs: fs => replaceText(fs, "/src/tests/tsconfig.json", `"esModuleInterop": false`, `"esModuleInterop": true`), + expectedDiagnostics: [ + getExpectedDiagnosticForProjectsInBuild("src/tests/tsconfig.json"), + [Diagnostics.Project_0_is_out_of_date_because_oldest_output_1_is_older_than_newest_input_2, "src/tests/tsconfig.json", "src/tests/index.js", "src/tests/tsconfig.json"], + [Diagnostics.Building_project_0, "/src/tests/tsconfig.json"] + ] + }, + outputFiles: [ + "/src/core/anotherModule.js", + "/src/core/index.js", + "/src/logic/index.js", + "/src/tests/index.js", + "/src/tests/tsconfig.json", + "/src/tests/tsconfig.tsbuildinfo" + ], + baselineOnly: true, + verifyDiagnostics: true + }); }); }); } diff --git a/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js new file mode 100644 index 00000000000..7903e8e54ec --- /dev/null +++ b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js @@ -0,0 +1,107 @@ +//// [/src/logic/index.js] +"use strict"; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +exports.__esModule = true; +var c = __importStar(require("../core/index")); +function getSecondsInDay() { + return c.multiply(10, 15); +} +exports.getSecondsInDay = getSecondsInDay; +var mod = __importStar(require("../core/anotherModule")); +exports.m = mod; + + +//// [/src/tests/index.js] +"use strict"; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +exports.__esModule = true; +var c = __importStar(require("../core/index")); +var logic = __importStar(require("../logic/index")); +c.leftPad("", 10); +logic.getSecondsInDay(); +var mod = __importStar(require("../core/anotherModule")); +exports.m = mod; + + +//// [/src/tests/tsconfig.json] +{ + "compilerOptions": { + "incremental": true, + "module": "commonjs", + "esModuleInterop": true + } +} + +//// [/src/tests/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "../core/index.ts": { + "version": "-18749805970", + "signature": "1874987148" + }, + "../core/anothermodule.ts": { + "version": "-2676574883", + "signature": "-8396256275" + }, + "../logic/index.ts": { + "version": "-5786964698", + "signature": "-6548680073" + }, + "./index.ts": { + "version": "12336236525", + "signature": "-9209611" + } + }, + "options": { + "incremental": true, + "module": 1, + "esModuleInterop": true, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": { + "../logic/index.ts": [ + "../core/anothermodule.ts", + "../core/index.ts" + ], + "./index.ts": [ + "../core/anothermodule.ts", + "../core/index.ts", + "../logic/index.ts" + ] + }, + "exportedModulesMap": { + "../logic/index.ts": [ + "../core/anothermodule.ts" + ], + "./index.ts": [ + "../core/anothermodule.ts" + ] + }, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "../core/anothermodule.ts", + "../core/index.ts", + "../logic/index.ts", + "./index.ts" + ] + }, + "version": "FakeTSVersion" +} + diff --git a/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-module-option-changes.js b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-module-option-changes.js new file mode 100644 index 00000000000..a73ad73c155 --- /dev/null +++ b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-module-option-changes.js @@ -0,0 +1,66 @@ +//// [/src/core/anotherModule.js] +define(["require", "exports"], function (require, exports) { + "use strict"; + exports.__esModule = true; + exports.World = "hello"; +}); + + +//// [/src/core/index.js] +define(["require", "exports"], function (require, exports) { + "use strict"; + exports.__esModule = true; + exports.someString = "HELLO WORLD"; + function leftPad(s, n) { return s + n; } + exports.leftPad = leftPad; + function multiply(a, b) { return a * b; } + exports.multiply = multiply; +}); + + +//// [/src/core/tsconfig.json] +{ + "compilerOptions": { + "incremental": true, + "module": "amd" + } +} + +//// [/src/core/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "./anothermodule.ts": { + "version": "-2676574883", + "signature": "-8396256275" + }, + "./index.ts": { + "version": "-18749805970", + "signature": "1874987148" + }, + "./some_decl.d.ts": { + "version": "-9253692965", + "signature": "-9253692965" + } + }, + "options": { + "incremental": true, + "module": 2, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": {}, + "exportedModulesMap": {}, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "./anothermodule.ts", + "./index.ts", + "./some_decl.d.ts" + ] + }, + "version": "FakeTSVersion" +} + diff --git a/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js new file mode 100644 index 00000000000..a92838c1418 --- /dev/null +++ b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js @@ -0,0 +1,109 @@ +//// [/src/core/anotherModule.js] +"use strict"; +exports.__esModule = true; +exports.World = "hello"; + + +//// [/src/core/index.js] +"use strict"; +exports.__esModule = true; +exports.someString = "HELLO WORLD"; +function leftPad(s, n) { return s + n; } +exports.leftPad = leftPad; +function multiply(a, b) { return a * b; } +exports.multiply = multiply; + + +//// [/src/logic/index.js] +"use strict"; +exports.__esModule = true; +var c = require("../core/index"); +function getSecondsInDay() { + return c.multiply(10, 15); +} +exports.getSecondsInDay = getSecondsInDay; +var mod = require("../core/anotherModule"); +exports.m = mod; + + +//// [/src/tests/index.js] +"use strict"; +exports.__esModule = true; +var c = require("../core/index"); +var logic = require("../logic/index"); +c.leftPad("", 10); +logic.getSecondsInDay(); +var mod = require("../core/anotherModule"); +exports.m = mod; + + +//// [/src/tests/tsconfig.json] +{ + "compilerOptions": { + "incremental": true, + "module": "commonjs", + "esModuleInterop": false + } +} + +//// [/src/tests/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "../core/index.ts": { + "version": "-18749805970", + "signature": "1874987148" + }, + "../core/anothermodule.ts": { + "version": "-2676574883", + "signature": "-8396256275" + }, + "../logic/index.ts": { + "version": "-5786964698", + "signature": "-6548680073" + }, + "./index.ts": { + "version": "12336236525", + "signature": "-9209611" + } + }, + "options": { + "incremental": true, + "module": 1, + "esModuleInterop": false, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": { + "../logic/index.ts": [ + "../core/anothermodule.ts", + "../core/index.ts" + ], + "./index.ts": [ + "../core/anothermodule.ts", + "../core/index.ts", + "../logic/index.ts" + ] + }, + "exportedModulesMap": { + "../logic/index.ts": [ + "../core/anothermodule.ts" + ], + "./index.ts": [ + "../core/anothermodule.ts" + ] + }, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "../core/anothermodule.ts", + "../core/index.ts", + "../logic/index.ts", + "./index.ts" + ] + }, + "version": "FakeTSVersion" +} + diff --git a/tests/baselines/reference/tsbuild/sample1/initial-Build/when-module-option-changes.js b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-module-option-changes.js new file mode 100644 index 00000000000..54e0f764dac --- /dev/null +++ b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-module-option-changes.js @@ -0,0 +1,62 @@ +//// [/src/core/anotherModule.js] +"use strict"; +exports.__esModule = true; +exports.World = "hello"; + + +//// [/src/core/index.js] +"use strict"; +exports.__esModule = true; +exports.someString = "HELLO WORLD"; +function leftPad(s, n) { return s + n; } +exports.leftPad = leftPad; +function multiply(a, b) { return a * b; } +exports.multiply = multiply; + + +//// [/src/core/tsconfig.json] +{ + "compilerOptions": { + "incremental": true, + "module": "commonjs" + } +} + +//// [/src/core/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "./anothermodule.ts": { + "version": "-2676574883", + "signature": "-8396256275" + }, + "./index.ts": { + "version": "-18749805970", + "signature": "1874987148" + }, + "./some_decl.d.ts": { + "version": "-9253692965", + "signature": "-9253692965" + } + }, + "options": { + "incremental": true, + "module": 1, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": {}, + "exportedModulesMap": {}, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "./anothermodule.ts", + "./index.ts", + "./some_decl.d.ts" + ] + }, + "version": "FakeTSVersion" +} + From fefb857847c89923d80016835e8089f08ffdba80 Mon Sep 17 00:00:00 2001 From: Nathan Shively-Sanders <293473+sandersn@users.noreply.github.com> Date: Sat, 29 Jun 2019 08:05:10 -0700 Subject: [PATCH 09/10] Use only immediately preceding JSDoc Now only the immediately preceding jsdoc of a node is retrieved by getJSDoc, although it still does the correct non-local lookup for nodes like ParameterDeclaration. This doesn't change parsing or binding, which use the per-node Node.jsdoc property directly. But it does change everything that relies on getJSDoc, which includes the checker and language service. Fixes #32062, which contains the analysis that justifies the change. --- src/compiler/utilities.ts | 4 +- .../baselines/reference/syntaxErrors.symbols | 4 -- tests/baselines/reference/syntaxErrors.types | 16 ++++---- .../cases/fourslash/commentsCommentParsing.ts | 40 +++++++++---------- .../fourslash/server/jsdocCallbackTag.ts | 9 ++--- 5 files changed, 33 insertions(+), 40 deletions(-) diff --git a/src/compiler/utilities.ts b/src/compiler/utilities.ts index ae5b60cd864..75a447d6dae 100644 --- a/src/compiler/utilities.ts +++ b/src/compiler/utilities.ts @@ -2201,13 +2201,13 @@ namespace ts { let result: (JSDoc | JSDocTag)[] | undefined; // Pull parameter comments from declaring function as well if (isVariableLike(hostNode) && hasInitializer(hostNode) && hasJSDocNodes(hostNode.initializer!)) { - result = addRange(result, (hostNode.initializer as HasJSDoc).jsDoc!); + result = append(result, last((hostNode.initializer as HasJSDoc).jsDoc!)); } let node: Node | undefined = hostNode; while (node && node.parent) { if (hasJSDocNodes(node)) { - result = addRange(result, node.jsDoc!); + result = append(result, last(node.jsDoc!)); } if (node.kind === SyntaxKind.Parameter) { diff --git a/tests/baselines/reference/syntaxErrors.symbols b/tests/baselines/reference/syntaxErrors.symbols index 2062b13c0b9..e28b5de936f 100644 --- a/tests/baselines/reference/syntaxErrors.symbols +++ b/tests/baselines/reference/syntaxErrors.symbols @@ -17,12 +17,8 @@ function f(x, y, skipped) { >skipped : Symbol(skipped, Decl(badTypeArguments.js, 4, 16)) return x.t + y.t; ->x.t : Symbol(C.t, Decl(dummyType.d.ts, 0, 20)) >x : Symbol(x, Decl(badTypeArguments.js, 4, 11)) ->t : Symbol(C.t, Decl(dummyType.d.ts, 0, 20)) ->y.t : Symbol(C.t, Decl(dummyType.d.ts, 0, 20)) >y : Symbol(y, Decl(badTypeArguments.js, 4, 13)) ->t : Symbol(C.t, Decl(dummyType.d.ts, 0, 20)) } var x = f({ t: 1000 }, { t: 3000 }, { t: 5000 }); >x : Symbol(x, Decl(badTypeArguments.js, 7, 3)) diff --git a/tests/baselines/reference/syntaxErrors.types b/tests/baselines/reference/syntaxErrors.types index c9af0176008..874a6857515 100644 --- a/tests/baselines/reference/syntaxErrors.types +++ b/tests/baselines/reference/syntaxErrors.types @@ -9,24 +9,24 @@ declare class C { t: T } // @ts-ignore /** @param {C.} skipped */ function f(x, y, skipped) { ->f : (x: C, y: C, skipped: C) => any ->x : C ->y : C +>f : (x: any, y: any, skipped: C) => any +>x : any +>y : any >skipped : C return x.t + y.t; >x.t + y.t : any >x.t : any ->x : C +>x : any +>t : any +>y.t : any +>y : any >t : any ->y.t : number ->y : C ->t : number } var x = f({ t: 1000 }, { t: 3000 }, { t: 5000 }); >x : any >f({ t: 1000 }, { t: 3000 }, { t: 5000 }) : any ->f : (x: C, y: C, skipped: C) => any +>f : (x: any, y: any, skipped: C) => any >{ t: 1000 } : { t: number; } >t : number >1000 : 1000 diff --git a/tests/cases/fourslash/commentsCommentParsing.ts b/tests/cases/fourslash/commentsCommentParsing.ts index fe3d44d3e6a..4731194ba69 100644 --- a/tests/cases/fourslash/commentsCommentParsing.ts +++ b/tests/cases/fourslash/commentsCommentParsing.ts @@ -26,7 +26,7 @@ ////} ////jsDocM/*4q*/ultiLine(/*4*/); //// -/////** this is multiple line jsdoc stule comment +/////** multiple line jsdoc comments no longer merge ////*New line1 ////*New Line2*/ /////** Shoul mege this line as well @@ -99,13 +99,13 @@ //// return /*18*/a + b; ////} /////*15*/s/*16q*/um(/*16*/10, /*17*/20); -/////** This is multiplication function*/ -/////** @param */ -/////** @param a first number*/ -/////** @param b */ -/////** @param c { -//// @param d @anotherTag*/ -/////** @param e LastParam @anotherTag*/ +/////** This is multiplication function +//// * @param +//// * @param a first number +//// * @param b +//// * @param c { +//// @param d @anotherTag +//// * @param e LastParam @anotherTag*/ ////function multiply(/*19aq*/a: number, /*20aq*/b: number, /*21aq*/c?: number, /*22aq*/d?, /*23aq*/e?) { ////} ////mult/*19q*/iply(/*19*/10,/*20*/ 20,/*21*/ 30, /*22*/40, /*23*/50); @@ -214,26 +214,26 @@ verify.quickInfoAt("3q", "function jsDocSingleLine(): void", "this is eg of sing verify.signatureHelp({ marker: "4", docComment: "this is multiple line jsdoc stule comment\nNew line1\nNew Line2" }); verify.quickInfoAt("4q", "function jsDocMultiLine(): void", "this is multiple line jsdoc stule comment\nNew line1\nNew Line2"); -verify.signatureHelp({ marker: "5", docComment: "this is multiple line jsdoc stule comment\nNew line1\nNew Line2\nShoul mege this line as well\nand this too\nAnother this one too" }); -verify.quickInfoAt("5q", "function jsDocMultiLineMerge(): void", "this is multiple line jsdoc stule comment\nNew line1\nNew Line2\nShoul mege this line as well\nand this too\nAnother this one too"); +verify.signatureHelp({ marker: "5", docComment: "Another this one too" }); +verify.quickInfoAt("5q", "function jsDocMultiLineMerge(): void", "Another this one too"); verify.signatureHelp({ marker: "6", docComment: "jsdoc comment" }); verify.quickInfoAt("6q", "function jsDocMixedComments1(): void", "jsdoc comment"); -verify.signatureHelp({ marker: "7", docComment: "jsdoc comment\nanother jsDocComment" }); -verify.quickInfoAt("7q", "function jsDocMixedComments2(): void", "jsdoc comment\nanother jsDocComment"); +verify.signatureHelp({ marker: "7", docComment: "another jsDocComment" }); +verify.quickInfoAt("7q", "function jsDocMixedComments2(): void", "another jsDocComment"); -verify.signatureHelp({ marker: "8", docComment: "jsdoc comment\n* triplestar jsDocComment" }); -verify.quickInfoAt("8q", "function jsDocMixedComments3(): void", "jsdoc comment\n* triplestar jsDocComment"); +verify.signatureHelp({ marker: "8", docComment: "* triplestar jsDocComment" }); +verify.quickInfoAt("8q", "function jsDocMixedComments3(): void", "* triplestar jsDocComment"); -verify.signatureHelp({ marker: "9", docComment: "jsdoc comment\nanother jsDocComment" }); -verify.quickInfoAt("9q", "function jsDocMixedComments4(): void", "jsdoc comment\nanother jsDocComment"); +verify.signatureHelp({ marker: "9", docComment: "another jsDocComment" }); +verify.quickInfoAt("9q", "function jsDocMixedComments4(): void", "another jsDocComment"); -verify.signatureHelp({ marker: "10", docComment: "jsdoc comment\nanother jsDocComment" }); -verify.quickInfoAt("10q", "function jsDocMixedComments5(): void", "jsdoc comment\nanother jsDocComment"); +verify.signatureHelp({ marker: "10", docComment: "another jsDocComment" }); +verify.quickInfoAt("10q", "function jsDocMixedComments5(): void", "another jsDocComment"); -verify.signatureHelp({ marker: "11", docComment: "another jsDocComment\njsdoc comment" }); -verify.quickInfoAt("11q", "function jsDocMixedComments6(): void", "another jsDocComment\njsdoc comment"); +verify.signatureHelp({ marker: "11", docComment: "jsdoc comment" }); +verify.quickInfoAt("11q", "function jsDocMixedComments6(): void", "jsdoc comment"); verify.signatureHelp({ marker: "12", docComment: "" }); verify.quickInfoAt("12q", "function noHelpComment1(): void"); diff --git a/tests/cases/fourslash/server/jsdocCallbackTag.ts b/tests/cases/fourslash/server/jsdocCallbackTag.ts index 700419cd682..1d754c08608 100644 --- a/tests/cases/fourslash/server/jsdocCallbackTag.ts +++ b/tests/cases/fourslash/server/jsdocCallbackTag.ts @@ -37,18 +37,15 @@ verify.signatureHelp({ marker: '4', text: "t(eventName: string, eventName2: string | number, eventName3: any): number", parameterDocComment: "- So many words", - tags: [{ name: "callback", text: "FooHandler - A kind of magic" }, - { name: "type", text: "{FooHandler} callback" }] + tags: [{ name: "type", text: "{FooHandler} callback" }] }); verify.signatureHelp({ marker: '5', parameterDocComment: "- Silence is golden", - tags: [{ name: "callback", text: "FooHandler - A kind of magic" }, - { name: "type", text: "{FooHandler} callback" }] + tags: [{ name: "type", text: "{FooHandler} callback" }] }); verify.signatureHelp({ marker: '6', parameterDocComment: "- Osterreich mos def", - tags: [{ name: "callback", text: "FooHandler - A kind of magic" }, - { name: "type", text: "{FooHandler} callback" }] + tags: [{ name: "type", text: "{FooHandler} callback" }] }); From c30054de633f395ee81f94477195115dca71a3d9 Mon Sep 17 00:00:00 2001 From: Austin Cummings Date: Sun, 30 Jun 2019 11:06:00 -0700 Subject: [PATCH 10/10] Fix esModuleInterop affectsEmit change test --- src/testRunner/unittests/tsbuild/sample.ts | 32 ++-- .../when-esModuleInterop-option-changes.js | 59 +++---- .../when-esModuleInterop-option-changes.js | 160 ++++++++++++++++-- 3 files changed, 187 insertions(+), 64 deletions(-) diff --git a/src/testRunner/unittests/tsbuild/sample.ts b/src/testRunner/unittests/tsbuild/sample.ts index a75cc9e8765..420c7a468aa 100644 --- a/src/testRunner/unittests/tsbuild/sample.ts +++ b/src/testRunner/unittests/tsbuild/sample.ts @@ -982,34 +982,40 @@ class someClass { }`), lastProjectOutputJs: "/src/tests/index.js", initialBuild: { modifyFs: fs => fs.writeFileSync("/src/tests/tsconfig.json", `{ + "references": [ + { "path": "../core" }, + { "path": "../logic" } + ], + "files": ["index.ts"], "compilerOptions": { - "incremental": true, - "module": "commonjs", + "composite": true, + "declaration": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, "esModuleInterop": false } }`), expectedDiagnostics: [ - getExpectedDiagnosticForProjectsInBuild("src/tests/tsconfig.json"), + getExpectedDiagnosticForProjectsInBuild("src/core/tsconfig.json", "src/logic/tsconfig.json", "src/tests/tsconfig.json"), + [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/core/tsconfig.json", "src/core/anotherModule.js"], + [Diagnostics.Building_project_0, "/src/core/tsconfig.json"], + [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/logic/tsconfig.json", "src/logic/index.js"], + [Diagnostics.Building_project_0, "/src/logic/tsconfig.json"], [Diagnostics.Project_0_is_out_of_date_because_output_file_1_does_not_exist, "src/tests/tsconfig.json", "src/tests/index.js"], - [Diagnostics.Building_project_0, "/src/tests/tsconfig.json"], + [Diagnostics.Building_project_0, "/src/tests/tsconfig.json"] ] }, incrementalDtsChangedBuild: { modifyFs: fs => replaceText(fs, "/src/tests/tsconfig.json", `"esModuleInterop": false`, `"esModuleInterop": true`), expectedDiagnostics: [ - getExpectedDiagnosticForProjectsInBuild("src/tests/tsconfig.json"), + getExpectedDiagnosticForProjectsInBuild("src/core/tsconfig.json", "src/logic/tsconfig.json", "src/tests/tsconfig.json"), + [Diagnostics.Project_0_is_up_to_date_because_newest_input_1_is_older_than_oldest_output_2, "src/core/tsconfig.json", "src/core/anotherModule.ts", "src/core/anotherModule.js"], + [Diagnostics.Project_0_is_up_to_date_because_newest_input_1_is_older_than_oldest_output_2, "src/logic/tsconfig.json", "src/logic/index.ts", "src/logic/index.js"], [Diagnostics.Project_0_is_out_of_date_because_oldest_output_1_is_older_than_newest_input_2, "src/tests/tsconfig.json", "src/tests/index.js", "src/tests/tsconfig.json"], [Diagnostics.Building_project_0, "/src/tests/tsconfig.json"] ] }, - outputFiles: [ - "/src/core/anotherModule.js", - "/src/core/index.js", - "/src/logic/index.js", - "/src/tests/index.js", - "/src/tests/tsconfig.json", - "/src/tests/tsconfig.tsbuildinfo" - ], + outputFiles: [], baselineOnly: true, verifyDiagnostics: true }); diff --git a/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js index 7903e8e54ec..28c559ee72a 100644 --- a/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js +++ b/tests/baselines/reference/tsbuild/sample1/incremental-declaration-changes/when-esModuleInterop-option-changes.js @@ -1,22 +1,3 @@ -//// [/src/logic/index.js] -"use strict"; -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; - result["default"] = mod; - return result; -}; -exports.__esModule = true; -var c = __importStar(require("../core/index")); -function getSecondsInDay() { - return c.multiply(10, 15); -} -exports.getSecondsInDay = getSecondsInDay; -var mod = __importStar(require("../core/anotherModule")); -exports.m = mod; - - //// [/src/tests/index.js] "use strict"; var __importStar = (this && this.__importStar) || function (mod) { @@ -37,9 +18,16 @@ exports.m = mod; //// [/src/tests/tsconfig.json] { + "references": [ + { "path": "../core" }, + { "path": "../logic" } + ], + "files": ["index.ts"], "compilerOptions": { - "incremental": true, - "module": "commonjs", + "composite": true, + "declaration": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, "esModuleInterop": true } } @@ -53,15 +41,15 @@ exports.m = mod; "signature": "-15964756381" }, "../core/index.ts": { - "version": "-18749805970", - "signature": "1874987148" + "version": "-13851440507", + "signature": "-13851440507" }, "../core/anothermodule.ts": { - "version": "-2676574883", - "signature": "-8396256275" + "version": "7652028357", + "signature": "7652028357" }, "../logic/index.ts": { - "version": "-5786964698", + "version": "-6548680073", "signature": "-6548680073" }, "./index.ts": { @@ -70,28 +58,29 @@ exports.m = mod; } }, "options": { - "incremental": true, - "module": 1, + "composite": true, + "declaration": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, "esModuleInterop": true, "configFilePath": "./tsconfig.json" }, "referencedMap": { "../logic/index.ts": [ - "../core/anothermodule.ts", - "../core/index.ts" + "../core/anothermodule.d.ts" ], "./index.ts": [ - "../core/anothermodule.ts", - "../core/index.ts", - "../logic/index.ts" + "../core/anothermodule.d.ts", + "../core/index.d.ts", + "../logic/index.d.ts" ] }, "exportedModulesMap": { "../logic/index.ts": [ - "../core/anothermodule.ts" + "../core/anothermodule.d.ts" ], "./index.ts": [ - "../core/anothermodule.ts" + "../core/anothermodule.d.ts" ] }, "semanticDiagnosticsPerFile": [ diff --git a/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js index a92838c1418..b6f0b53b89c 100644 --- a/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js +++ b/tests/baselines/reference/tsbuild/sample1/initial-Build/when-esModuleInterop-option-changes.js @@ -1,9 +1,25 @@ +//// [/src/core/anotherModule.d.ts] +export declare const World = "hello"; +//# sourceMappingURL=anotherModule.d.ts.map + +//// [/src/core/anotherModule.d.ts.map] +{"version":3,"file":"anotherModule.d.ts","sourceRoot":"","sources":["anotherModule.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,KAAK,UAAU,CAAC"} + //// [/src/core/anotherModule.js] "use strict"; exports.__esModule = true; exports.World = "hello"; +//// [/src/core/index.d.ts] +export declare const someString: string; +export declare function leftPad(s: string, n: number): string; +export declare function multiply(a: number, b: number): number; +//# sourceMappingURL=index.d.ts.map + +//// [/src/core/index.d.ts.map] +{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,UAAU,EAAE,MAAsB,CAAC;AAChD,wBAAgB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,UAAmB;AAC/D,wBAAgB,QAAQ,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,UAAmB"} + //// [/src/core/index.js] "use strict"; exports.__esModule = true; @@ -14,6 +30,52 @@ function multiply(a, b) { return a * b; } exports.multiply = multiply; +//// [/src/core/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "./anothermodule.ts": { + "version": "-2676574883", + "signature": "25219880154" + }, + "./index.ts": { + "version": "-18749805970", + "signature": "11051732871" + }, + "./some_decl.d.ts": { + "version": "-9253692965", + "signature": "-9253692965" + } + }, + "options": { + "composite": true, + "declaration": true, + "declarationMap": true, + "skipDefaultLibCheck": true, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": {}, + "exportedModulesMap": {}, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "./anothermodule.ts", + "./index.ts", + "./some_decl.d.ts" + ] + }, + "version": "FakeTSVersion" +} + +//// [/src/logic/index.d.ts] +export declare function getSecondsInDay(): number; +import * as mod from '../core/anotherModule'; +export declare const m: typeof mod; + + //// [/src/logic/index.js] "use strict"; exports.__esModule = true; @@ -24,6 +86,64 @@ function getSecondsInDay() { exports.getSecondsInDay = getSecondsInDay; var mod = require("../core/anotherModule"); exports.m = mod; +//# sourceMappingURL=index.js.map + +//// [/src/logic/index.js.map] +{"version":3,"file":"index.js","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":";;AAAA,iCAAmC;AACnC,SAAgB,eAAe;IAC3B,OAAO,CAAC,CAAC,QAAQ,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC;AAC9B,CAAC;AAFD,0CAEC;AACD,2CAA6C;AAChC,QAAA,CAAC,GAAG,GAAG,CAAC"} + +//// [/src/logic/tsconfig.tsbuildinfo] +{ + "program": { + "fileInfos": { + "../../lib/lib.d.ts": { + "version": "-15964756381", + "signature": "-15964756381" + }, + "../core/index.ts": { + "version": "-13851440507", + "signature": "-13851440507" + }, + "../core/anothermodule.ts": { + "version": "7652028357", + "signature": "7652028357" + }, + "./index.ts": { + "version": "-5786964698", + "signature": "-6548680073" + } + }, + "options": { + "composite": true, + "declaration": true, + "sourceMap": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, + "configFilePath": "./tsconfig.json" + }, + "referencedMap": { + "./index.ts": [ + "../core/anothermodule.d.ts", + "../core/index.d.ts" + ] + }, + "exportedModulesMap": { + "./index.ts": [ + "../core/anothermodule.d.ts" + ] + }, + "semanticDiagnosticsPerFile": [ + "../../lib/lib.d.ts", + "../core/anothermodule.ts", + "../core/index.ts", + "./index.ts" + ] + }, + "version": "FakeTSVersion" +} + +//// [/src/tests/index.d.ts] +import * as mod from '../core/anotherModule'; +export declare const m: typeof mod; //// [/src/tests/index.js] @@ -39,9 +159,16 @@ exports.m = mod; //// [/src/tests/tsconfig.json] { + "references": [ + { "path": "../core" }, + { "path": "../logic" } + ], + "files": ["index.ts"], "compilerOptions": { - "incremental": true, - "module": "commonjs", + "composite": true, + "declaration": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, "esModuleInterop": false } } @@ -55,15 +182,15 @@ exports.m = mod; "signature": "-15964756381" }, "../core/index.ts": { - "version": "-18749805970", - "signature": "1874987148" + "version": "-13851440507", + "signature": "-13851440507" }, "../core/anothermodule.ts": { - "version": "-2676574883", - "signature": "-8396256275" + "version": "7652028357", + "signature": "7652028357" }, "../logic/index.ts": { - "version": "-5786964698", + "version": "-6548680073", "signature": "-6548680073" }, "./index.ts": { @@ -72,28 +199,29 @@ exports.m = mod; } }, "options": { - "incremental": true, - "module": 1, + "composite": true, + "declaration": true, + "forceConsistentCasingInFileNames": true, + "skipDefaultLibCheck": true, "esModuleInterop": false, "configFilePath": "./tsconfig.json" }, "referencedMap": { "../logic/index.ts": [ - "../core/anothermodule.ts", - "../core/index.ts" + "../core/anothermodule.d.ts" ], "./index.ts": [ - "../core/anothermodule.ts", - "../core/index.ts", - "../logic/index.ts" + "../core/anothermodule.d.ts", + "../core/index.d.ts", + "../logic/index.d.ts" ] }, "exportedModulesMap": { "../logic/index.ts": [ - "../core/anothermodule.ts" + "../core/anothermodule.d.ts" ], "./index.ts": [ - "../core/anothermodule.ts" + "../core/anothermodule.d.ts" ] }, "semanticDiagnosticsPerFile": [