Skip to content

Possible regression in 3.4 with distributive conditional types #30569

Closed
@dragomirtitian

Description

@dragomirtitian

TypeScript Version: 3.4.0-dev.201xxxxx

Search Terms:

Code

type UnionKeys<T> = T extends any ? keyof T : never;
type BugHelper<T, TAll> = T extends any ? Exclude<UnionKeys<TAll>, keyof T> : never
type Bug<TAll> =  BugHelper<TAll, TAll>
type R = Bug<{ a : any } | { b: any }> // "a" | "b" in 3.3, never in 3.4

Expected behavior:
R should be "a" | "b" (as it previously was in 3.3)

Actual behavior:
R is never in 3.4

Playground Link: link

Related Issues: Probably cause by #29437, #30489

The code above is a simplification of the StrictUnion type I posted on SO, and this issue was reported there as a comment. The type was also included by another SO user in SimplyTyped

Workaround
For the StrictUnion type a simple workaround is to pass in union keys to StrictUnionHelper. This will achieve the same result as in 3.4:

type StrictUnionHelper<T, TAllKeys extends PropertyKey> = T extends any ? T & Partial<Record<Exclude<TAllKeys, keyof T>, never>> : never;
type StrictUnion<T> = StrictUnionHelper<T, UnionKeys<T>>

If breaking change is intended, I would like some guidance on whether the workaround version is likely to remain stable in the next releases or if there is a fundamental issue with the idea behind the type.

Metadata

Metadata

Assignees

Labels

BugA bug in TypeScript

Type

No type

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions