Code below is abridged and in screenshots. You can see a full working example here.
I have a small function which wraps Promise.all
, returning the resolved values in an object instead of an array:
const allPromiseMap = async <T extends { [KEY in string]: unknown }>(map: {
[KEY in keyof T]: Promise<T[KEY]>;
}): Promise<T> => {
// ...
};
The idea is you pass in an object with Promise
values and get back an object with the same keys but the resolved type from Promise
as values.
Testing with some simple code, everything looks fine:
(async () => {
const promises: {
hello: Promise<string>;
world?: Promise<number>;
} = {
hello: new Promise(() => { })
}
const responseMap = await allPromiseMap(promises);
const worldResponse = responseMap.world;
})();
Even the optional tag on world
is preserved!
However, when trying to store world
in another variable, undefined
is removed from the type:
For comparison, similar code without my function does not have this problem:
I'm pretty sure this is some bit of meta type-data hanging on to my object behaving incorrectly so barring that this is expected behavior: Is there a better way I could type my function to avoid this behavior?
This is a fun one.
It's not about underlined. It's possibly non existing properties, with your function, it knows they exist. You are telling it to add all the keys.
Change world to become: world: Promise<number | undefined>
and it will work.