Is there a way to make TypeScript infer the type of the callback
parameter inside the funcAorB
function correctly? While TypeScript can deduce the type of the callback
parameter when calling funcAorB
, it fails to do so within the body of funcAorB
. I was expecting TypeScript to use the same type as inferred for the data
parameter throughout the function, given that it accurately determines the type of the data
parameter based on the key
member in the switch
statement.
I appreciate that TypeScript infers the type of callback
correctly when calling funcAorB
, but I wish this inference extended to the internals of funcAorB
.
type DataA = {
readonly key: 'a',
};
type DataB = {
readonly key: 'b',
};
function funcA(data: DataA, callback: (data: DataA) => void) {}
function funcB(data: DataB, callback: (data: DataB) => void) {}
function funcAorB<T extends DataA | DataB>(data: T, callback: (data: T) => void) {
switch (data.key) {
case 'a': {
// TypeScript believes that data is of type DataA now.
// However, I need to use "as" because of TypeScript's assumption that
// callback could be ((data: DataA) => void | (data: DataB) => void).
funcA(data, callback as (data: DataA) => void);
break;
}
case 'b': {
// TypeScript believes that data is of type DataB now.
// However, I need to use "as" because of TypeScript's assumption that
// callback could be ((data: DataA) => void | (data: DataB) => void).
funcB(data, callback as (data: DataB) => void);
break;
}
}
}
// The callback type is inferred properly at the call site.
funcAorB({ key: 'a' }, (data) => {
// This works because data is inferred to be DataA.
const a: 'a' = data.key;
});
// The callback type is inferred properly at the call site.
funcAorB({ key: 'b' }, (data) => {
// This works because data is inferred to be DataB.
const b: 'b' = data.key;
});