-
Notifications
You must be signed in to change notification settings - Fork 13.2k
Description
🔎 Search Terms
"type predicate", "infer", "discriminated union"
🕗 Version & Regression Information
tested on 5.5.0-dev20240318, 5.5.0-dev20240326
- I was unable to test this on prior versions because it requires Infer type predicates from function bodies using control flow analysis #57465 which was only merged recently.
⏯ Playground Link
💻 Code
declare const foobar: { type: 'foo'; foo: number } | { type: 'bar'; bar: string };
if (foobar.type === 'foo') {
foobar.foo;
}
const pred = (fb: typeof foobar) => fb.type === 'foo';
if (pred(foobar)) {
foobar.foo;
}
declare const foobars: (typeof foobar)[];
foobars.filter(fb => fb.type === 'foo').map(({ foo }) => foo);🙁 Actual behavior
Line 6’s pred and the anonymous function passed to the foobars.filter method on line 12 are each inferred as (fb: typeof foobar) => boolean, leading to the errors on lines 8 and 12. Both errors are, unsurprisingly,
Property 'foo' does not exist on type '{ type: "foo"; foo: number; } | { type: "bar"; bar: string; }'.
🙂 Expected behavior
The predicates on lines 6 and 12 should be inferred as (fb: typeof foobar) => fb is { type: "foo"; foo: number; }, so they narrow foobar the same way the inline condition on line 2 does.
Additional information about the issue
This is a very-new feature, and from reading the PR it’s clear that it is (intentionally) not everything it could be yet, but as far as I can tell based on #57465 (and the fact that it closed my prior suggestion #50734), these predicates should be inferred correctly here. If I misunderstand, then I suppose this should have been a feature request rather than a bug report, but the point remains that this is a massive limitation in this feature, since the overwhelming majority of type predicates our project deals with are discriminated unions of this sort.