Repository navigation
Inferred type changes from 5.5 to 5.6 #60077
Description
Activity
Andarist commented
on Sep 26, 2024 ContributorMore actionsThis seems related to #59764 but I'm not sure it's the same
I think this boils down to the same issue and I would refer to Ryan's comments there: #59764 (comment) and #59764 (comment)
Those are just heuristics and there are no perfect answers to which type should be preferred. Some cases perform better with one candidate picked and some cases perform better with the other one picked.
I think that especially the case presented by Ryan in the first linked comment sways this way more in favor of the covariant candidate. It's way more likely that the object's shape available at runtime will have the properties coming from a covariant argument position than those coming from a contravariant parameter.
Reacted by Dan Vanderkam and Ryan Cavanaugh- addedQuestionAn issue which isn't directly actionable in codeAn issue which isn't directly actionable in code
on Sep 26, 2024 RyanCavanaugh commented
on Sep 26, 2024 MemberMore actionsI agree with Mateusz Burzyński (@Andarist) that I was correct in those comments 🙂
OK, I can see I'm outgunned here. 🙂
FWIW, I do think it's a bit surprising that this wasn't mentioned in the release notes given that it can cause confusing changes when you upgrade — I only found the PR via
every-ts bisect.Though I guess looking at #59764 (comment) a little more closely, one difference is that in that case, the widened type of
defaultTisn't assignable toFoo(at least with excess property checking). Whereas in my example the type ofinitis assignable toProps, so that seems like a more natural type to infer.I can see that there's no perfect answer in Ryan's case, but it seems there is here.
Andarist commented
on Sep 27, 2024 ContributorMore actionsThat is a difference that I implicitly talked about here. Honestly, I don't know how to think about this in the TS's structural type system since there are tradeoffs to both approaches
- locked as resolved and limited conversation to collaborators
on Oct 22, 2025
🔎 Search Terms
🕗 Version & Regression Information
every-ts)⏯ Playground Link
https://www.typescriptlang.org/play/?ts=5.6.2#code/CYUwxgNghgTiAEYD2A7AzgF3gMwFzwB4AFAPgAoAoeHFfMgBxiXrXyIEp4BeE+ANyQBLYABoq8QSkEYA-GzGce8IgG4KFSRhAxsUMAiJMW8AN7i4AR3yYYkgOZrqzWdYy2UDigF91ydFkZmNG4cSmoGNiM0RV4AclixahN4S3wAIjT4LwU1CkCWADpnCgB6EvgAURgmGAkUeAAVAGV4AFYCgDYReBQkLEl4EFgIQW1+bTRBVDQKIA
💻 Code
🙁 Actual behavior
Pis inferred as{req: string}, so accessing the optional property causes a TypeScript error.🙂 Expected behavior
Pshould be inferred asProps, as it is in TS 5.5 (and earlier). If you drop theinitparameter from the call tof, thenPis also inferred to bePropsin TS 5.6.Additional information about the issue
This seems related to #59764 but I'm not sure it's the same, so I figured I'd file an issue. I tried the same code on the playground for #59709 and it does not fix this issue.
cc Mateusz Burzyński (@Andarist) for whether TS 5.6 is right and I'm wrong 😄