From d5fd17bf0bcdad1a347a36cb567feb2283357567 Mon Sep 17 00:00:00 2001 From: Matt McCutchen Date: Sat, 7 Jul 2018 16:27:23 -0400 Subject: [PATCH] Fix crash in elaborateElementwise when the target property is known but it doesn't have a declaration (e.g., in a mapped type). Fixes #25498. --- src/compiler/checker.ts | 4 ++-- .../baselines/reference/errorElaboration.errors.txt | 12 +++++++++++- tests/baselines/reference/errorElaboration.js | 10 ++++++++++ tests/baselines/reference/errorElaboration.symbols | 11 +++++++++++ tests/baselines/reference/errorElaboration.types | 13 +++++++++++++ tests/cases/compiler/errorElaboration.ts | 6 ++++++ 6 files changed, 53 insertions(+), 3 deletions(-) diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index d6a35037761..a72367a4cda 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -10367,9 +10367,9 @@ namespace ts { } } - if (!issuedElaboration && (length(targetProp && targetProp.declarations) || length(target.symbol && target.symbol.declarations))) { + if (!issuedElaboration && (targetProp && length(targetProp.declarations) || target.symbol && length(target.symbol.declarations))) { addRelatedInfo(reportedDiag, createDiagnosticForNode( - targetProp ? targetProp.declarations[0] : target.symbol.declarations[0], + targetProp && length(targetProp.declarations) ? targetProp.declarations[0] : target.symbol.declarations[0], Diagnostics.The_expected_type_comes_from_property_0_which_is_declared_here_on_type_1, propertyName && !(nameType.flags & TypeFlags.UniqueESSymbol) ? unescapeLeadingUnderscores(propertyName) : typeToString(nameType), typeToString(target) diff --git a/tests/baselines/reference/errorElaboration.errors.txt b/tests/baselines/reference/errorElaboration.errors.txt index 94742d7d98b..57971cad269 100644 --- a/tests/baselines/reference/errorElaboration.errors.txt +++ b/tests/baselines/reference/errorElaboration.errors.txt @@ -2,9 +2,10 @@ tests/cases/compiler/errorElaboration.ts(12,5): error TS2345: Argument of type ' Type 'Container>' is not assignable to type 'Container>'. Type 'Ref' is not assignable to type 'Ref'. Type 'string' is not assignable to type 'number'. +tests/cases/compiler/errorElaboration.ts(17,11): error TS2322: Type '"bar"' is not assignable to type '"foo"'. -==== tests/cases/compiler/errorElaboration.ts (1 errors) ==== +==== tests/cases/compiler/errorElaboration.ts (2 errors) ==== // Repro for #5712 interface Ref { @@ -22,4 +23,13 @@ tests/cases/compiler/errorElaboration.ts(12,5): error TS2345: Argument of type ' !!! error TS2345: Type 'Container>' is not assignable to type 'Container>'. !!! error TS2345: Type 'Ref' is not assignable to type 'Ref'. !!! error TS2345: Type 'string' is not assignable to type 'number'. + + // Repro for #25498 + + function test(): {[A in "foo"]: A} { + return {foo: "bar"}; + ~~~ +!!! error TS2322: Type '"bar"' is not assignable to type '"foo"'. +!!! related TS6500 tests/cases/compiler/errorElaboration.ts:16:18: The expected type comes from property 'foo' which is declared here on type '{ foo: "foo"; }' + } \ No newline at end of file diff --git a/tests/baselines/reference/errorElaboration.js b/tests/baselines/reference/errorElaboration.js index eed8bbd7c6b..c1dd0a470d3 100644 --- a/tests/baselines/reference/errorElaboration.js +++ b/tests/baselines/reference/errorElaboration.js @@ -11,9 +11,19 @@ interface Container { declare function foo(x: () => Container>): void; let a: () => Container>; foo(a); + +// Repro for #25498 + +function test(): {[A in "foo"]: A} { + return {foo: "bar"}; +} //// [errorElaboration.js] // Repro for #5712 var a; foo(a); +// Repro for #25498 +function test() { + return { foo: "bar" }; +} diff --git a/tests/baselines/reference/errorElaboration.symbols b/tests/baselines/reference/errorElaboration.symbols index 72206e3caef..839b19c0599 100644 --- a/tests/baselines/reference/errorElaboration.symbols +++ b/tests/baselines/reference/errorElaboration.symbols @@ -38,3 +38,14 @@ foo(a); >foo : Symbol(foo, Decl(errorElaboration.ts, 8, 1)) >a : Symbol(a, Decl(errorElaboration.ts, 10, 3)) +// Repro for #25498 + +function test(): {[A in "foo"]: A} { +>test : Symbol(test, Decl(errorElaboration.ts, 11, 7)) +>A : Symbol(A, Decl(errorElaboration.ts, 15, 19)) +>A : Symbol(A, Decl(errorElaboration.ts, 15, 19)) + + return {foo: "bar"}; +>foo : Symbol(foo, Decl(errorElaboration.ts, 16, 10)) +} + diff --git a/tests/baselines/reference/errorElaboration.types b/tests/baselines/reference/errorElaboration.types index 96aaba6ce30..385ab481bb2 100644 --- a/tests/baselines/reference/errorElaboration.types +++ b/tests/baselines/reference/errorElaboration.types @@ -39,3 +39,16 @@ foo(a); >foo : (x: () => Container>) => void >a : () => Container> +// Repro for #25498 + +function test(): {[A in "foo"]: A} { +>test : () => { foo: "foo"; } +>A : A +>A : A + + return {foo: "bar"}; +>{foo: "bar"} : { foo: "bar"; } +>foo : "bar" +>"bar" : "bar" +} + diff --git a/tests/cases/compiler/errorElaboration.ts b/tests/cases/compiler/errorElaboration.ts index 97ec0dde61c..87575f1df11 100644 --- a/tests/cases/compiler/errorElaboration.ts +++ b/tests/cases/compiler/errorElaboration.ts @@ -10,3 +10,9 @@ interface Container { declare function foo(x: () => Container>): void; let a: () => Container>; foo(a); + +// Repro for #25498 + +function test(): {[A in "foo"]: A} { + return {foo: "bar"}; +}