Skip to content

Conditional type check on type inferred from mapped type false negative #33366

@ksabry

Description

@ksabry

TypeScript Version: 3.7.0-dev.20190910

Also tested in 3.6.2, 3.5.2

Search Terms:

conditional mapped inference inferred

Code

// Simple mapped type and inferrence
type Mapped<T> = { [K in keyof T]: { name: T[K] } };
type InferFromMapped<T> = T extends Mapped<infer R> ? R : never;

// Object literal type and associated mapped type
// Note that in the real code we don't have a direct reference to LiteralType
type LiteralType = {
	first: "first";
	second: "second";
}
type MappedLiteralType = {
	first: { name: "first" },
	second: { name: "second" },
};

type Inferred = InferFromMapped<MappedLiteralType>;

// UNEXPECTED resolves to false
type Test1 = Inferred extends Record<any, string> ? true : false;

// true as expected
type Test2 = LiteralType extends Record<any, string> ? true : false;

// true as expected; currently using this as a workaround
type Test3 = Inferred extends Record<keyof Inferred, string> ? true : false;

Expected behavior:

As Inferred and LiteralType are equivalent, we would expect Inferred extends Record<any, string> to resolve to true just as the case with LiteralType does.

Actual behavior:

Test1 resolves to false. This has the same behavior for similar expressions of the record (e.g. Record<string, string>, { [key: string]: string }); interestingly though, if we write the record Record<keyof Inferred, string> we get the expected behavior, this is the current workaround I'm using.

We also get the expected behavior if we instead defined MappedLiteralType as Mapped<LiteralType>. However in the code I encountered this, we have no direct access to LiteralType, only Inferred; I added LiteralType to the example only for demonstration of the expected behavior.

Playground Link:

Playground

Related Issues:

Metadata

Metadata

Assignees

Labels

BugA bug in TypeScript

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions