Skip to content

Commit

Permalink
Don't inferFromIndexTypes() twice (#34501)
Browse files Browse the repository at this point in the history
* Don't inferFromIndexTypes() twice

* Add tests
  • Loading branch information
sandersn authored Mar 4, 2020
1 parent 5c8def9 commit 061338e
Show file tree
Hide file tree
Showing 10 changed files with 145 additions and 36 deletions.
52 changes: 26 additions & 26 deletions src/compiler/checker.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18537,6 +18537,32 @@ namespace ts {
}
// Infer from the members of source and target only if the two types are possibly related
if (!typesDefinitelyUnrelated(source, target)) {
if (isArrayType(source) || isTupleType(source)) {
if (isTupleType(target)) {
const sourceLength = isTupleType(source) ? getLengthOfTupleType(source) : 0;
const targetLength = getLengthOfTupleType(target);
const sourceRestType = isTupleType(source) ? getRestTypeOfTupleType(source) : getElementTypeOfArrayType(source);
const targetRestType = getRestTypeOfTupleType(target);
const fixedLength = targetLength < sourceLength || sourceRestType ? targetLength : sourceLength;
for (let i = 0; i < fixedLength; i++) {
inferFromTypes(i < sourceLength ? getTypeArguments(<TypeReference>source)[i] : sourceRestType!, getTypeArguments(target)[i]);
}
if (targetRestType) {
const types = fixedLength < sourceLength ? getTypeArguments(<TypeReference>source).slice(fixedLength, sourceLength) : [];
if (sourceRestType) {
types.push(sourceRestType);
}
if (types.length) {
inferFromTypes(getUnionType(types), targetRestType);
}
}
return;
}
if (isArrayType(target)) {
inferFromIndexTypes(source, target);
return;
}
}
inferFromProperties(source, target);
inferFromSignatures(source, target, SignatureKind.Call);
inferFromSignatures(source, target, SignatureKind.Construct);
Expand All @@ -18545,32 +18571,6 @@ namespace ts {
}

function inferFromProperties(source: Type, target: Type) {
if (isArrayType(source) || isTupleType(source)) {
if (isTupleType(target)) {
const sourceLength = isTupleType(source) ? getLengthOfTupleType(source) : 0;
const targetLength = getLengthOfTupleType(target);
const sourceRestType = isTupleType(source) ? getRestTypeOfTupleType(source) : getElementTypeOfArrayType(source);
const targetRestType = getRestTypeOfTupleType(target);
const fixedLength = targetLength < sourceLength || sourceRestType ? targetLength : sourceLength;
for (let i = 0; i < fixedLength; i++) {
inferFromTypes(i < sourceLength ? getTypeArguments(<TypeReference>source)[i] : sourceRestType!, getTypeArguments(target)[i]);
}
if (targetRestType) {
const types = fixedLength < sourceLength ? getTypeArguments(<TypeReference>source).slice(fixedLength, sourceLength) : [];
if (sourceRestType) {
types.push(sourceRestType);
}
if (types.length) {
inferFromTypes(getUnionType(types), targetRestType);
}
}
return;
}
if (isArrayType(target)) {
inferFromIndexTypes(source, target);
return;
}
}
const properties = getPropertiesOfObjectType(target);
for (const targetProp of properties) {
const sourceProp = getPropertyOfType(source, targetProp.escapedName);
Expand Down
8 changes: 7 additions & 1 deletion tests/baselines/reference/correctOrderOfPromiseMethod.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ async function countEverything(): Promise<number> {
const [resultA, resultB] = await Promise.all([
providerA(),
providerB(),
] as const);
]);

const dataA: A[] = resultA;
const dataB: B[] = resultB;
Expand All @@ -24,6 +24,10 @@ async function countEverything(): Promise<number> {
}
return 0;
}

// #31179

const expected: Promise<["a", "b", "c"]> = Promise.all(undefined as readonly ["a", "b", "c"]);


//// [correctOrderOfPromiseMethod.js]
Expand Down Expand Up @@ -92,3 +96,5 @@ function countEverything() {
});
});
}
// #31179
var expected = Promise.all(undefined);
12 changes: 11 additions & 1 deletion tests/baselines/reference/correctOrderOfPromiseMethod.symbols
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ async function countEverything(): Promise<number> {
providerB(),
>providerB : Symbol(providerB, Decl(correctOrderOfPromiseMethod.ts, 11, 9))

] as const);
]);

const dataA: A[] = resultA;
>dataA : Symbol(dataA, Decl(correctOrderOfPromiseMethod.ts, 18, 9))
Expand All @@ -70,3 +70,13 @@ async function countEverything(): Promise<number> {
return 0;
}

// #31179

const expected: Promise<["a", "b", "c"]> = Promise.all(undefined as readonly ["a", "b", "c"]);
>expected : Symbol(expected, Decl(correctOrderOfPromiseMethod.ts, 28, 5))
>Promise : Symbol(Promise, Decl(lib.es5.d.ts, --, --), Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.symbol.wellknown.d.ts, --, --))
>Promise.all : Symbol(PromiseConstructor.all, Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --) ... and 6 more)
>Promise : Symbol(Promise, Decl(lib.es5.d.ts, --, --), Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.symbol.wellknown.d.ts, --, --))
>all : Symbol(PromiseConstructor.all, Decl(lib.es2015.iterable.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --), Decl(lib.es2015.promise.d.ts, --, --) ... and 6 more)
>undefined : Symbol(undefined)

20 changes: 15 additions & 5 deletions tests/baselines/reference/correctOrderOfPromiseMethod.types
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,12 @@ async function countEverything(): Promise<number> {
const [resultA, resultB] = await Promise.all([
>resultA : A[]
>resultB : B[]
>await Promise.all([ providerA(), providerB(), ] as const) : [A[], B[]]
>Promise.all([ providerA(), providerB(), ] as const) : Promise<[A[], B[]]>
>await Promise.all([ providerA(), providerB(), ]) : [A[], B[]]
>Promise.all([ providerA(), providerB(), ]) : Promise<[A[], B[]]>
>Promise.all : { <TAll>(values: Iterable<TAll | PromiseLike<TAll>>): Promise<TAll[]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>, T10 | PromiseLike<T10>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9, T10]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9]>; <T1, T2, T3, T4, T5, T6, T7, T8>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8]>; <T1, T2, T3, T4, T5, T6, T7>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>]): Promise<[T1, T2, T3, T4, T5, T6, T7]>; <T1, T2, T3, T4, T5, T6>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>]): Promise<[T1, T2, T3, T4, T5, T6]>; <T1, T2, T3, T4, T5>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>]): Promise<[T1, T2, T3, T4, T5]>; <T1, T2, T3, T4>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>]): Promise<[T1, T2, T3, T4]>; <T1, T2, T3>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>]): Promise<[T1, T2, T3]>; <T1, T2>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>]): Promise<[T1, T2]>; <T>(values: readonly (T | PromiseLike<T>)[]): Promise<T[]>; }
>Promise : PromiseConstructor
>all : { <TAll>(values: Iterable<TAll | PromiseLike<TAll>>): Promise<TAll[]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>, T10 | PromiseLike<T10>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9, T10]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9]>; <T1, T2, T3, T4, T5, T6, T7, T8>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8]>; <T1, T2, T3, T4, T5, T6, T7>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>]): Promise<[T1, T2, T3, T4, T5, T6, T7]>; <T1, T2, T3, T4, T5, T6>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>]): Promise<[T1, T2, T3, T4, T5, T6]>; <T1, T2, T3, T4, T5>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>]): Promise<[T1, T2, T3, T4, T5]>; <T1, T2, T3, T4>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>]): Promise<[T1, T2, T3, T4]>; <T1, T2, T3>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>]): Promise<[T1, T2, T3]>; <T1, T2>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>]): Promise<[T1, T2]>; <T>(values: readonly (T | PromiseLike<T>)[]): Promise<T[]>; }
>[ providerA(), providerB(), ] as const : readonly [Promise<A[]>, Promise<B[]>]
>[ providerA(), providerB(), ] : readonly [Promise<A[]>, Promise<B[]>]
>[ providerA(), providerB(), ] : [Promise<A[]>, Promise<B[]>]

providerA(),
>providerA() : Promise<A[]>
Expand All @@ -44,7 +43,7 @@ async function countEverything(): Promise<number> {
>providerB() : Promise<B[]>
>providerB : () => Promise<B[]>

] as const);
]);

const dataA: A[] = resultA;
>dataA : A[]
Expand Down Expand Up @@ -72,3 +71,14 @@ async function countEverything(): Promise<number> {
>0 : 0
}

// #31179

const expected: Promise<["a", "b", "c"]> = Promise.all(undefined as readonly ["a", "b", "c"]);
>expected : Promise<["a", "b", "c"]>
>Promise.all(undefined as readonly ["a", "b", "c"]) : Promise<["a", "b", "c"]>
>Promise.all : { <TAll>(values: Iterable<TAll | PromiseLike<TAll>>): Promise<TAll[]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>, T10 | PromiseLike<T10>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9, T10]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9]>; <T1, T2, T3, T4, T5, T6, T7, T8>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8]>; <T1, T2, T3, T4, T5, T6, T7>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>]): Promise<[T1, T2, T3, T4, T5, T6, T7]>; <T1, T2, T3, T4, T5, T6>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>]): Promise<[T1, T2, T3, T4, T5, T6]>; <T1, T2, T3, T4, T5>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>]): Promise<[T1, T2, T3, T4, T5]>; <T1, T2, T3, T4>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>]): Promise<[T1, T2, T3, T4]>; <T1, T2, T3>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>]): Promise<[T1, T2, T3]>; <T1, T2>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>]): Promise<[T1, T2]>; <T>(values: readonly (T | PromiseLike<T>)[]): Promise<T[]>; }
>Promise : PromiseConstructor
>all : { <TAll>(values: Iterable<TAll | PromiseLike<TAll>>): Promise<TAll[]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9, T10>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>, T10 | PromiseLike<T10>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9, T10]>; <T1, T2, T3, T4, T5, T6, T7, T8, T9>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>, T9 | PromiseLike<T9>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8, T9]>; <T1, T2, T3, T4, T5, T6, T7, T8>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>, T8 | PromiseLike<T8>]): Promise<[T1, T2, T3, T4, T5, T6, T7, T8]>; <T1, T2, T3, T4, T5, T6, T7>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>, T7 | PromiseLike<T7>]): Promise<[T1, T2, T3, T4, T5, T6, T7]>; <T1, T2, T3, T4, T5, T6>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>, T6 | PromiseLike<T6>]): Promise<[T1, T2, T3, T4, T5, T6]>; <T1, T2, T3, T4, T5>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>, T5 | PromiseLike<T5>]): Promise<[T1, T2, T3, T4, T5]>; <T1, T2, T3, T4>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>, T4 | PromiseLike<T4>]): Promise<[T1, T2, T3, T4]>; <T1, T2, T3>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>, T3 | PromiseLike<T3>]): Promise<[T1, T2, T3]>; <T1, T2>(values: readonly [T1 | PromiseLike<T1>, T2 | PromiseLike<T2>]): Promise<[T1, T2]>; <T>(values: readonly (T | PromiseLike<T>)[]): Promise<T[]>; }
>undefined as readonly ["a", "b", "c"] : readonly ["a", "b", "c"]
>undefined : undefined

2 changes: 1 addition & 1 deletion tests/baselines/reference/restTupleElements1.types
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,7 @@ f0([]); // Error
>[] : []

f0([1]);
>f0([1]) : [number, number]
>f0([1]) : [number, unknown]
>f0 : <T, U>(x: [T, ...U[]]) => [T, U]
>[1] : [number]
>1 : 1
Expand Down
11 changes: 11 additions & 0 deletions tests/baselines/reference/typeInferenceWithTupleType.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,14 @@ var zipResult = zip(["foo", "bar"], [5, 6]);
var zipResultEle = zipResult[0]; // [string, number]
var zipResultEleEle = zipResult[0][0]; // string

// #33559 and #33752

declare function f1<T1, T2>(values: [T1[], T2[]]): T1;
declare function f2<T1, T2>(values: readonly [T1[], T2[]]): T1;

let expected: "a";
expected = f1(undefined as ["a"[], "b"[]]);
expected = f2(undefined as ["a"[], "b"[]]);


//// [typeInferenceWithTupleType.js]
Expand All @@ -46,3 +54,6 @@ function zip(array1, array2) {
var zipResult = zip(["foo", "bar"], [5, 6]);
var zipResultEle = zipResult[0]; // [string, number]
var zipResultEleEle = zipResult[0][0]; // string
var expected;
expected = f1(undefined);
expected = f2(undefined);
32 changes: 32 additions & 0 deletions tests/baselines/reference/typeInferenceWithTupleType.symbols
Original file line number Diff line number Diff line change
Expand Up @@ -97,4 +97,36 @@ var zipResultEleEle = zipResult[0][0]; // string
>0 : Symbol(0)
>0 : Symbol(0)

// #33559 and #33752

declare function f1<T1, T2>(values: [T1[], T2[]]): T1;
>f1 : Symbol(f1, Decl(typeInferenceWithTupleType.ts, 22, 38))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 26, 20))
>T2 : Symbol(T2, Decl(typeInferenceWithTupleType.ts, 26, 23))
>values : Symbol(values, Decl(typeInferenceWithTupleType.ts, 26, 28))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 26, 20))
>T2 : Symbol(T2, Decl(typeInferenceWithTupleType.ts, 26, 23))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 26, 20))

declare function f2<T1, T2>(values: readonly [T1[], T2[]]): T1;
>f2 : Symbol(f2, Decl(typeInferenceWithTupleType.ts, 26, 54))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 27, 20))
>T2 : Symbol(T2, Decl(typeInferenceWithTupleType.ts, 27, 23))
>values : Symbol(values, Decl(typeInferenceWithTupleType.ts, 27, 28))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 27, 20))
>T2 : Symbol(T2, Decl(typeInferenceWithTupleType.ts, 27, 23))
>T1 : Symbol(T1, Decl(typeInferenceWithTupleType.ts, 27, 20))

let expected: "a";
>expected : Symbol(expected, Decl(typeInferenceWithTupleType.ts, 29, 3))

expected = f1(undefined as ["a"[], "b"[]]);
>expected : Symbol(expected, Decl(typeInferenceWithTupleType.ts, 29, 3))
>f1 : Symbol(f1, Decl(typeInferenceWithTupleType.ts, 22, 38))
>undefined : Symbol(undefined)

expected = f2(undefined as ["a"[], "b"[]]);
>expected : Symbol(expected, Decl(typeInferenceWithTupleType.ts, 29, 3))
>f2 : Symbol(f2, Decl(typeInferenceWithTupleType.ts, 26, 54))
>undefined : Symbol(undefined)

28 changes: 28 additions & 0 deletions tests/baselines/reference/typeInferenceWithTupleType.types
Original file line number Diff line number Diff line change
Expand Up @@ -109,4 +109,32 @@ var zipResultEleEle = zipResult[0][0]; // string
>0 : 0
>0 : 0

// #33559 and #33752

declare function f1<T1, T2>(values: [T1[], T2[]]): T1;
>f1 : <T1, T2>(values: [T1[], T2[]]) => T1
>values : [T1[], T2[]]

declare function f2<T1, T2>(values: readonly [T1[], T2[]]): T1;
>f2 : <T1, T2>(values: readonly [T1[], T2[]]) => T1
>values : readonly [T1[], T2[]]

let expected: "a";
>expected : "a"

expected = f1(undefined as ["a"[], "b"[]]);
>expected = f1(undefined as ["a"[], "b"[]]) : "a"
>expected : "a"
>f1(undefined as ["a"[], "b"[]]) : "a"
>f1 : <T1, T2>(values: [T1[], T2[]]) => T1
>undefined as ["a"[], "b"[]] : ["a"[], "b"[]]
>undefined : undefined

expected = f2(undefined as ["a"[], "b"[]]);
>expected = f2(undefined as ["a"[], "b"[]]) : "a"
>expected : "a"
>f2(undefined as ["a"[], "b"[]]) : "a"
>f2 : <T1, T2>(values: readonly [T1[], T2[]]) => T1
>undefined as ["a"[], "b"[]] : ["a"[], "b"[]]
>undefined : undefined

6 changes: 5 additions & 1 deletion tests/cases/compiler/correctOrderOfPromiseMethod.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ async function countEverything(): Promise<number> {
const [resultA, resultB] = await Promise.all([
providerA(),
providerB(),
] as const);
]);

const dataA: A[] = resultA;
const dataB: B[] = resultB;
Expand All @@ -26,3 +26,7 @@ async function countEverything(): Promise<number> {
}
return 0;
}

// #31179

const expected: Promise<["a", "b", "c"]> = Promise.all(undefined as readonly ["a", "b", "c"]);
Loading

0 comments on commit 061338e

Please sign in to comment.