Last active
May 13, 2022 03:34
-
-
Save intrnl/692d5401b0a45e27602f2a4ca0972b55 to your computer and use it in GitHub Desktop.
Race promises into settled values with concurrency limit
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
async function* raceAllSettled (iterable, concurrency = 4) { | |
const executing = new Set(); | |
const consume = async () => { | |
const value = await Promise.race(executing); | |
executing.delete(value.promise); | |
delete value.promise; | |
return value; | |
}; | |
for (const item of iterable) { | |
const promise = promised(item).then( | |
(value) => ({ status: 'fulfilled', value, promise }), | |
(reason) => ({ status: 'rejected', reason, promise }), | |
); | |
executing.add(promise); | |
if (executing.size >= concurrency) { | |
yield await consume(); | |
} | |
} | |
while (executing.size) { | |
yield await consume(); | |
} | |
} | |
const promised = (value) => { | |
return (value && value.then) ? value : Promise.resolve(value); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const promises = [ | |
new Promise((resolve) => setTimeout(resolve, 1000, 456)), | |
123, | |
Promise.resolve(234), | |
Promise.reject(345), | |
]; | |
for await (const value of raceAllSettled(promises)) { | |
console.log(value); | |
} | |
// > { status: 'fulfilled', value: 123 } | |
// > { status: 'fulfilled', value: 234 } | |
// > { status: 'rejected', value: 345 } | |
// > { status: 'fulfilled', value: 456 } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment