diff --git a/src/compiler/checker.ts b/src/compiler/checker.ts index 2c8cc77ada14d..5d67431022a1e 100644 --- a/src/compiler/checker.ts +++ b/src/compiler/checker.ts @@ -23665,7 +23665,7 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { const sourceArity = getTypeReferenceArity(source); const targetArity = getTypeReferenceArity(target); const sourceRestFlag = isTupleType(source) ? source.target.combinedFlags & ElementFlags.Rest : ElementFlags.Rest; - const targetRestFlag = target.target.combinedFlags & ElementFlags.Rest; + const targetHasRestElement = !!(target.target.combinedFlags & ElementFlags.Variable); const sourceMinLength = isTupleType(source) ? source.target.minLength : 0; const targetMinLength = target.target.minLength; if (!sourceRestFlag && sourceArity < targetMinLength) { @@ -23674,13 +23674,13 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { } return Ternary.False; } - if (!targetRestFlag && targetArity < sourceMinLength) { + if (!targetHasRestElement && targetArity < sourceMinLength) { if (reportErrors) { reportError(Diagnostics.Source_has_0_element_s_but_target_allows_only_1, sourceMinLength, targetArity); } return Ternary.False; } - if (!targetRestFlag && (sourceRestFlag || targetArity < sourceArity)) { + if (!targetHasRestElement && (sourceRestFlag || targetArity < sourceArity)) { if (reportErrors) { if (sourceMinLength < targetMinLength) { reportError(Diagnostics.Target_requires_0_element_s_but_source_may_have_fewer, targetMinLength); @@ -23695,7 +23695,6 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker { const targetTypeArguments = getTypeArguments(target); const targetStartCount = getStartElementCount(target.target, ElementFlags.NonRest); const targetEndCount = getEndElementCount(target.target, ElementFlags.NonRest); - const targetHasRestElement = target.target.hasRestElement; let canExcludeDiscriminants = !!excludedProperties; for (let sourcePosition = 0; sourcePosition < sourceArity; sourcePosition++) { const sourceFlags = isTupleType(source) ? source.target.elementFlags[sourcePosition] : ElementFlags.Rest; diff --git a/tests/baselines/reference/variadicTuples1.errors.txt b/tests/baselines/reference/variadicTuples1.errors.txt index fbc7d599c6ff0..bc68ea7f4476e 100644 --- a/tests/baselines/reference/variadicTuples1.errors.txt +++ b/tests/baselines/reference/variadicTuples1.errors.txt @@ -5,9 +5,9 @@ variadicTuples1.ts(62,5): error TS2345: Argument of type '[]' is not assignable variadicTuples1.ts(131,9): error TS2344: Type 'V' does not satisfy the constraint 'unknown[]'. The type 'readonly unknown[]' is 'readonly' and cannot be assigned to the mutable type 'unknown[]'. variadicTuples1.ts(149,5): error TS2322: Type '[string, ...unknown[]]' is not assignable to type '[string, ...T]'. - Target requires 2 element(s) but source may have fewer. + Source provides no match for variadic element at position 1 in target. variadicTuples1.ts(151,5): error TS2322: Type '[string, ...unknown[]]' is not assignable to type '[string, ...U]'. - Target requires 2 element(s) but source may have fewer. + Source provides no match for variadic element at position 1 in target. variadicTuples1.ts(152,5): error TS2322: Type '[string, ...T]' is not assignable to type '[string, ...U]'. Type at position 1 in source is not compatible with type at position 1 in target. Type 'T' is not assignable to type 'U'. @@ -22,7 +22,7 @@ variadicTuples1.ts(170,5): error TS2322: Type 'T' is not assignable to type '[.. variadicTuples1.ts(171,5): error TS4104: The type 'readonly [...T]' is 'readonly' and cannot be assigned to the mutable type '[...T]'. variadicTuples1.ts(181,5): error TS2322: Type 'T' is not assignable to type '[...U]'. Type 'string[]' is not assignable to type '[...U]'. - Target requires 1 element(s) but source may have fewer. + Source provides no match for variadic element at position 0 in target. variadicTuples1.ts(182,5): error TS2322: Type '[...T]' is not assignable to type '[...U]'. Type 'T' is not assignable to type 'U'. 'T' is assignable to the constraint of type 'U', but 'U' could be instantiated with a different subtype of constraint 'string[]'. @@ -211,12 +211,12 @@ variadicTuples1.ts(411,7): error TS2322: Type '[boolean, false]' is not assignab y = x; // Error ~ !!! error TS2322: Type '[string, ...unknown[]]' is not assignable to type '[string, ...T]'. -!!! error TS2322: Target requires 2 element(s) but source may have fewer. +!!! error TS2322: Source provides no match for variadic element at position 1 in target. y = z; z = x; // Error ~ !!! error TS2322: Type '[string, ...unknown[]]' is not assignable to type '[string, ...U]'. -!!! error TS2322: Target requires 2 element(s) but source may have fewer. +!!! error TS2322: Source provides no match for variadic element at position 1 in target. z = y; // Error ~ !!! error TS2322: Type '[string, ...T]' is not assignable to type '[string, ...U]'. @@ -268,7 +268,7 @@ variadicTuples1.ts(411,7): error TS2322: Type '[boolean, false]' is not assignab ~~ !!! error TS2322: Type 'T' is not assignable to type '[...U]'. !!! error TS2322: Type 'string[]' is not assignable to type '[...U]'. -!!! error TS2322: Target requires 1 element(s) but source may have fewer. +!!! error TS2322: Source provides no match for variadic element at position 0 in target. t2 = t1; // Error ~~ !!! error TS2322: Type '[...T]' is not assignable to type '[...U]'. diff --git a/tests/baselines/reference/variadicTuples2.errors.txt b/tests/baselines/reference/variadicTuples2.errors.txt index 9ae0ed7c394e3..269771a5f2691 100644 --- a/tests/baselines/reference/variadicTuples2.errors.txt +++ b/tests/baselines/reference/variadicTuples2.errors.txt @@ -38,7 +38,7 @@ variadicTuples2.ts(73,8): error TS2345: Argument of type '["abc", "def", true]' variadicTuples2.ts(76,5): error TS2322: Type '[number, number]' is not assignable to type '[number, ...T]'. Source provides no match for variadic element at position 1 in target. variadicTuples2.ts(77,5): error TS2322: Type '[number, ...number[]]' is not assignable to type '[number, ...T]'. - Target requires 2 element(s) but source may have fewer. + Source provides no match for variadic element at position 1 in target. variadicTuples2.ts(78,5): error TS2322: Type '[number, ...T]' is not assignable to type '[number, number]'. Type '[number, ...unknown[]]' is not assignable to type '[number, number]'. Target requires 2 element(s) but source may have fewer. @@ -208,7 +208,7 @@ variadicTuples2.ts(139,25): error TS2345: Argument of type '["blah2", 1, 2, 3]' x = z; // Error ~ !!! error TS2322: Type '[number, ...number[]]' is not assignable to type '[number, ...T]'. -!!! error TS2322: Target requires 2 element(s) but source may have fewer. +!!! error TS2322: Source provides no match for variadic element at position 1 in target. y = x; // Error ~ !!! error TS2322: Type '[number, ...T]' is not assignable to type '[number, number]'. diff --git a/tests/baselines/reference/variadicTuples3.errors.txt b/tests/baselines/reference/variadicTuples3.errors.txt new file mode 100644 index 0000000000000..34b62aecf6dc0 --- /dev/null +++ b/tests/baselines/reference/variadicTuples3.errors.txt @@ -0,0 +1,35 @@ +variadicTuples3.ts(5,3): error TS2322: Type 'any[]' is not assignable to type '[...T, ...P]'. + Source provides no match for variadic element at position 0 in target. +variadicTuples3.ts(10,3): error TS2322: Type '[any, any]' is not assignable to type '[...T, ...P]'. + Source provides no match for variadic element at position 0 in target. +variadicTuples3.ts(15,3): error TS2322: Type '[any, any, any]' is not assignable to type '[...T, ...P]'. + Source provides no match for variadic element at position 0 in target. + + +==== variadicTuples3.ts (3 errors) ==== + // https://github.com/microsoft/TypeScript/issues/58697 + + function test1(): [...T, ...P] { + let x: any[] = []; + return x; + ~~~~~~ +!!! error TS2322: Type 'any[]' is not assignable to type '[...T, ...P]'. +!!! error TS2322: Source provides no match for variadic element at position 0 in target. + } + + function test2(): [...T, ...P] { + let x: [any, any] = [null, null]; + return x; + ~~~~~~ +!!! error TS2322: Type '[any, any]' is not assignable to type '[...T, ...P]'. +!!! error TS2322: Source provides no match for variadic element at position 0 in target. + } + + function test3(): [...T, ...P] { + let x: [any, any, any] = [null, null, null]; + return x; + ~~~~~~ +!!! error TS2322: Type '[any, any, any]' is not assignable to type '[...T, ...P]'. +!!! error TS2322: Source provides no match for variadic element at position 0 in target. + } + \ No newline at end of file diff --git a/tests/baselines/reference/variadicTuples3.symbols b/tests/baselines/reference/variadicTuples3.symbols new file mode 100644 index 0000000000000..ed8c60440519c --- /dev/null +++ b/tests/baselines/reference/variadicTuples3.symbols @@ -0,0 +1,47 @@ +//// [tests/cases/conformance/types/tuple/variadicTuples3.ts] //// + +=== variadicTuples3.ts === +// https://github.com/microsoft/TypeScript/issues/58697 + +function test1(): [...T, ...P] { +>test1 : Symbol(test1, Decl(variadicTuples3.ts, 0, 0)) +>T : Symbol(T, Decl(variadicTuples3.ts, 2, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 2, 31)) +>T : Symbol(T, Decl(variadicTuples3.ts, 2, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 2, 31)) + + let x: any[] = []; +>x : Symbol(x, Decl(variadicTuples3.ts, 3, 5)) + + return x; +>x : Symbol(x, Decl(variadicTuples3.ts, 3, 5)) +} + +function test2(): [...T, ...P] { +>test2 : Symbol(test2, Decl(variadicTuples3.ts, 5, 1)) +>T : Symbol(T, Decl(variadicTuples3.ts, 7, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 7, 31)) +>T : Symbol(T, Decl(variadicTuples3.ts, 7, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 7, 31)) + + let x: [any, any] = [null, null]; +>x : Symbol(x, Decl(variadicTuples3.ts, 8, 5)) + + return x; +>x : Symbol(x, Decl(variadicTuples3.ts, 8, 5)) +} + +function test3(): [...T, ...P] { +>test3 : Symbol(test3, Decl(variadicTuples3.ts, 10, 1)) +>T : Symbol(T, Decl(variadicTuples3.ts, 12, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 12, 31)) +>T : Symbol(T, Decl(variadicTuples3.ts, 12, 15)) +>P : Symbol(P, Decl(variadicTuples3.ts, 12, 31)) + + let x: [any, any, any] = [null, null, null]; +>x : Symbol(x, Decl(variadicTuples3.ts, 13, 5)) + + return x; +>x : Symbol(x, Decl(variadicTuples3.ts, 13, 5)) +} + diff --git a/tests/baselines/reference/variadicTuples3.types b/tests/baselines/reference/variadicTuples3.types new file mode 100644 index 0000000000000..303507d764c71 --- /dev/null +++ b/tests/baselines/reference/variadicTuples3.types @@ -0,0 +1,50 @@ +//// [tests/cases/conformance/types/tuple/variadicTuples3.ts] //// + +=== variadicTuples3.ts === +// https://github.com/microsoft/TypeScript/issues/58697 + +function test1(): [...T, ...P] { +>test1 : () => [...T, ...P] +> : ^ ^^^^^^^^^ ^^ ^^^^^^^^^ ^^^^^^^ + + let x: any[] = []; +>x : any[] +> : ^^^^^ +>[] : never[] +> : ^^^^^^^ + + return x; +>x : any[] +> : ^^^^^ +} + +function test2(): [...T, ...P] { +>test2 : () => [...T, ...P] +> : ^ ^^^^^^^^^ ^^ ^^^^^^^^^ ^^^^^^^ + + let x: [any, any] = [null, null]; +>x : [any, any] +> : ^^^^^^^^^^ +>[null, null] : [null, null] +> : ^^^^^^^^^^^^ + + return x; +>x : [any, any] +> : ^^^^^^^^^^ +} + +function test3(): [...T, ...P] { +>test3 : () => [...T, ...P] +> : ^ ^^^^^^^^^ ^^ ^^^^^^^^^ ^^^^^^^ + + let x: [any, any, any] = [null, null, null]; +>x : [any, any, any] +> : ^^^^^^^^^^^^^^^ +>[null, null, null] : [null, null, null] +> : ^^^^^^^^^^^^^^^^^^ + + return x; +>x : [any, any, any] +> : ^^^^^^^^^^^^^^^ +} + diff --git a/tests/cases/conformance/types/tuple/variadicTuples3.ts b/tests/cases/conformance/types/tuple/variadicTuples3.ts new file mode 100644 index 0000000000000..40478e3ea6b08 --- /dev/null +++ b/tests/cases/conformance/types/tuple/variadicTuples3.ts @@ -0,0 +1,19 @@ +// @strict: true +// @noEmit: true + +// https://github.com/microsoft/TypeScript/issues/58697 + +function test1(): [...T, ...P] { + let x: any[] = []; + return x; +} + +function test2(): [...T, ...P] { + let x: [any, any] = [null, null]; + return x; +} + +function test3(): [...T, ...P] { + let x: [any, any, any] = [null, null, null]; + return x; +}