Skip to content

Inference doesn't find common base type for union with null or undefined - TypeScript 4.8 regression #49938

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
dragomirtitian opened this issue Jul 18, 2022 · 6 comments
Assignees
Labels
Bug A bug in TypeScript Fix Available A PR has been opened for this issue

Comments

@dragomirtitian
Copy link
Contributor

Bug Report

πŸ”Ž Search Terms

inference common base type null undefined

πŸ•— Version & Regression Information

  • This changed between versions 4.7.3 and 4.8-beta

⏯ Playground Link

Playground link with relevant code

πŸ’» Code

function equal<T>(a: T, b: T) { }

let v = null!;

// Object types with common base types

type B = { foo: string }
type D = { foo: string; bar: number }

// Error in 4.8 TS can't find common type ❌
// 4.7 T was undefined | B
equal(v as B, v as undefined | D)

// ok T is B βœ…
equal(v as B, v as D)
// ok T is B | undefined βœ…
equal(v as B, v as B | undefined)

πŸ™ Actual behavior

In 4.8 TypeScript can't find common base type between B and undefined | D. In 4.7 this used to be B | undefined.

This also happens for literal types and their respective base types as well as for arrays as shown in the 'Other Examples' in the playground link. I didn't include the code as the bug is the same, it's just different instances we found in our code.

πŸ™‚ Expected behavior

Typescript finds the type B | undefined for T as it did in 4.7.

@dragomirtitian
Copy link
Contributor Author

Also reported in Bloomberg feedback #49835

@jakebailey
Copy link
Member

This also bisects to #49119.

@jakebailey
Copy link
Member

jakebailey commented Jul 20, 2022

Also interestingly, if you write equal(v as D | undefined, v as B) (so, flip the argument order), T is inferred as D | undefined.

I'm a little confused as to why the argument order matters here, but given that the inference if you swap the arguments is the same in 4.7, it's nothing new.

Playground Link

@jakebailey
Copy link
Member

I pinned this down to this part of the PR: https://github.com/microsoft/TypeScript/pull/49119/files#diff-d9ab6589e714c71e657f601cf30ff51dfc607fc98419bf72e04f6b0fa92cc4b8R21147

This part of the code doesn't consider the fact that any of the types could be unions that contain null or undefined, only types which are exactly null or undefined. I have a fix which correctly retains null and undefined which fixes this issue but doesn't make things consistent in argument order (so, same as 4.7). Currently verifying that this is right and that I can't also fix the other case too, since it seems incongruent with other inferences.

@jakebailey
Copy link
Member

jakebailey commented Jul 21, 2022

My fix doesn't seem to be the right one; we should probably discuss the intended inference behavior here.

EDIT: Well, maybe it is, after fixing a few things: Playground Link

@ahejlsberg
Copy link
Member

Fixed by #50021.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Bug A bug in TypeScript Fix Available A PR has been opened for this issue
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants