JavaScriptã®äžŠè¡ã€ãã¬ãŒã¿ãŒã§äžŠååŠçãå®è£ ããããŒã¿éçŽåã¢ããªã®æ§èœãå€§å¹ ã«åäžãããæ¹æ³ã解説ããŸããå¹ççãªéåææäœã®å®çŸã«ã掻çšãã ããã
JavaScript䞊è¡ã€ãã¬ãŒã¿ãŒïŒããã©ãŒãã³ã¹ãåäžããã䞊ååŠç
é²åãç¶ããJavaScriptéçºã®äžçã«ãããŠãããã©ãŒãã³ã¹ã¯æãéèŠã§ããã¢ããªã±ãŒã·ã§ã³ãããè€éã§ããŒã¿éçŽåã«ãªãã«ã€ããŠãéçºè ã¯å®è¡é床ãšãªãœãŒã¹å©çšãæé©åããæè¡ãåžžã«æ¢ãæ±ããŠããŸãããã®æ¢æ±ã«ããã匷åãªããŒã«ã®äžã€ã䞊è¡ã€ãã¬ãŒã¿ãŒã§ããããã¯éåææäœã®äžŠååŠçãå¯èœã«ããç¹å®ã®ã·ããªãªã§å€§å¹ ãªããã©ãŒãã³ã¹åäžããããããŸãã
éåæã€ãã¬ãŒã¿ãŒã®çè§£
䞊è¡ã€ãã¬ãŒã¿ãŒã«é£ã³èŸŒãåã«ãJavaScriptã«ãããéåæã€ãã¬ãŒã¿ãŒã®åºæ¬ãææ¡ããããšãéèŠã§ããES6ã§å°å ¥ãããåŸæ¥ã®ã€ãã¬ãŒã¿ãŒã¯ãããŒã¿æ§é ãåæçã«èµ°æ»ããæ¹æ³ãæäŸããŸããããããAPIããã®ããŒã¿ååŸããã¡ã€ã«ã®èªã¿èŸŒã¿ãšãã£ãéåææäœãæ±ãå Žåãåæäœãå®äºããã®ãåŸ ã€éã¡ã€ã³ã¹ã¬ããããããã¯ãããããåŸæ¥ã®ã€ãã¬ãŒã¿ãŒã¯éå¹çã«ãªããŸãã
ES2018ã§å°å
¥ãããéåæã€ãã¬ãŒã¿ãŒã¯ãéåææäœãåŸ
ã€éãã€ãã¬ãŒã·ã§ã³ãäžæåæ¢ããã³åéã§ããããã«ããããšã§ããã®å¶éã«å¯ŸåŠããŸãããããã¯async颿°ãšPromiseã®æŠå¿µã«åºã¥ããŠããããã³ããããã³ã°ãªããŒã¿ååŸãå¯èœã«ããŸããéåæã€ãã¬ãŒã¿ãŒã¯ãvalueãšdoneããããã£ãå«ããªããžã§ã¯ãã§è§£æ±ºãããPromiseãè¿ãnext()ã¡ãœãããå®çŸ©ããŸããvalueã¯çŸåšã®èŠçŽ ã衚ããdoneã¯ã€ãã¬ãŒã·ã§ã³ãå®äºãããã©ããã瀺ããŸãã
以äžã«éåæã€ãã¬ãŒã¿ãŒã®åºæ¬çãªäŸã瀺ããŸãã
async function* asyncGenerator() {
yield await Promise.resolve(1);
yield await Promise.resolve(2);
yield await Promise.resolve(3);
}
const asyncIterator = asyncGenerator();
asyncIterator.next().then(result => console.log(result)); // { value: 1, done: false }
asyncIterator.next().then(result => console.log(result)); // { value: 2, done: false }
asyncIterator.next().then(result => console.log(result)); // { value: 3, done: false }
asyncIterator.next().then(result => console.log(result)); // { value: undefined, done: true }
ãã®äŸã¯ãPromiseãyieldããåçŽãªéåæãžã§ãã¬ãŒã¿ãŒã瀺ããŠããŸããasyncIterator.next()ã¡ãœããã¯ãã·ãŒã±ã³ã¹ã®æ¬¡ã®å€ã§è§£æ±ºãããPromiseãè¿ããŸããawaitããŒã¯ãŒãã«ãããæ¬¡ã®å€ãyieldãããåã«åPromiseã解決ãããããšãä¿èšŒãããŸãã
äžŠè¡æ§ã®å¿ èŠæ§ïŒããã«ããã¯ãžã®å¯ŸåŠ
éåæã€ãã¬ãŒã¿ãŒã¯ãéåææäœã®åŠçã«ãããŠåæã€ãã¬ãŒã¿ãŒãããå€§å¹ ãªæ¹åããããããŸãããããã§ãæäœãé æ¬¡å®è¡ããŸããåæäœãç¬ç«ããŠãããæéããããã·ããªãªã§ã¯ããã®é 次å®è¡ãããã«ããã¯ãšãªããå šäœã®ããã©ãŒãã³ã¹ãå¶éããå¯èœæ§ããããŸãã
äŸãã°ããããããç°ãªãå°åãåœã衚ãè€æ°ã®APIããããŒã¿ãååŸããå¿ èŠãããã·ããªãªãèããŠã¿ãŸããããæšæºçãªéåæã€ãã¬ãŒã¿ãŒã䜿çšãããšãäžã€ã®APIããããŒã¿ãååŸãããã®å¿çãåŸ ã£ãŠããæ¬¡ã®APIããããŒã¿ãååŸããããšããããšãç¹°ãè¿ããŸãããã®é 次çãªã¢ãããŒãã¯ãç¹ã«APIã®ã¬ã€ãã³ã·ãé«ãå Žåãã¬ãŒãå¶éãããå Žåã«éå¹çã«ãªãå¯èœæ§ããããŸãã
ããã§äžŠè¡ã€ãã¬ãŒã¿ãŒã®åºçªã§ãããããã¯éåææäœã®äžŠåå®è¡ãå¯èœã«ããè€æ°ã®APIããåæã«ããŒã¿ãååŸã§ããŸããJavaScriptã®äžŠè¡æ§ã¢ãã«ã掻çšããããšã§ãå šäœã®å®è¡æéãå€§å¹ ã«ççž®ããã¢ããªã±ãŒã·ã§ã³ã®å¿çæ§ãåäžãããããšãã§ããŸãã
䞊è¡ã€ãã¬ãŒã¿ãŒã®ç޹ä»
䞊è¡ã€ãã¬ãŒã¿ãŒã¯ãéåæã¿ã¹ã¯ã®äžŠåå®è¡ã管çããã«ã¹ã¿ã ãã«ãã®ã€ãã¬ãŒã¿ãŒã§ããããã¯JavaScriptã®çµã¿èŸŒã¿æ©èœã§ã¯ãªããèªèº«ã§å®è£
ãããã¿ãŒã³ã§ããäžå¿çãªèãæ¹ã¯ãè€æ°ã®éåææäœãåæã«éå§ããçµæãå©çšå¯èœã«ãªã次第yieldãããšãããã®ã§ããããã¯éåžžãPromiseãšPromise.all()ãŸãã¯Promise.race()ã¡ãœããããããŠã¢ã¯ãã£ããªã¿ã¹ã¯ã管çããã¡ã«ããºã ã䜿çšããŠå®çŸãããŸãã
䞊è¡ã€ãã¬ãŒã¿ãŒã®äž»èŠãªã³ã³ããŒãã³ãïŒ
- ã¿ã¹ã¯ãã¥ãŒïŒ å®è¡ãããéåæã¿ã¹ã¯ãä¿æãããã¥ãŒããããã®ã¿ã¹ã¯ã¯ãå€ãã®å ŽåãPromiseãè¿ã颿°ãšããŠè¡šãããŸãã
- åæå®è¡æ°å¶éïŒ åæã«å®è¡ã§ããã¿ã¹ã¯ã®æ°ã®äžéãããã«ãããããŸãã«ãå€ãã®äžŠåæäœã§ã·ã¹ãã ãéè² è·ã«ãªãã®ãé²ããŸãã
- ã¿ã¹ã¯ç®¡çïŒ æ°ããã¿ã¹ã¯ã®éå§ãå®äºããã¿ã¹ã¯ã®è¿œè·¡ããšã©ãŒåŠçãªã©ãã¿ã¹ã¯ã®å®è¡ã管çããããžãã¯ã
- çµæã®åŠçïŒ å®äºããã¿ã¹ã¯ã®çµæãå¶åŸ¡ãããæ¹æ³ã§yieldããããžãã¯ã
䞊è¡ã€ãã¬ãŒã¿ãŒã®å®è£ ïŒå®è·µçãªäŸ
å®è·µçãªäŸãçšããŠã䞊è¡ã€ãã¬ãŒã¿ãŒã®å®è£ ã説æããŸããããè€æ°ã®APIããåæã«ããŒã¿ãååŸããã·ãã¥ã¬ãŒã·ã§ã³ãè¡ããŸãã
async function* concurrentIterator(urls, concurrency) {
const taskQueue = [...urls];
const runningTasks = new Set();
async function runTask(url) {
runningTasks.add(url);
try {
const response = await fetch(url);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
yield data;
} catch (error) {
console.error(`Error fetching ${url}: ${error}`);
} finally {
runningTasks.delete(url);
if (taskQueue.length > 0) {
const nextUrl = taskQueue.shift();
runTask(nextUrl);
} else if (runningTasks.size === 0) {
// å
šãŠã®ã¿ã¹ã¯ãå®äº
}
}
}
// åæã®ã¿ã¹ã¯ã»ãããéå§
for (let i = 0; i < concurrency && taskQueue.length > 0; i++) {
const url = taskQueue.shift();
runTask(url);
}
}
// Example usage
const apiUrls = [
'https://rickandmortyapi.com/api/character/1', // ãªãã¯ã»ãµã³ãã§ã¹
'https://rickandmortyapi.com/api/character/2', // ã¢ãŒãã£ã»ã¹ãã¹
'https://rickandmortyapi.com/api/character/3', // ãµããŒã»ã¹ãã¹
'https://rickandmortyapi.com/api/character/4', // ãã¹ã»ã¹ãã¹
'https://rickandmortyapi.com/api/character/5' // ãžã§ãªãŒã»ã¹ãã¹
];
async function main() {
const concurrencyLimit = 2;
for await (const data of concurrentIterator(apiUrls, concurrencyLimit)) {
console.log('Received data:', data.name);
}
console.log('All data processed.');
}
main();
解説ïŒ
concurrentIterator颿°ã¯ãURLã®é åãšåæå®è¡æ°å¶éãå ¥åãšããŠåãåããŸãã- ååŸããURLãå«ã
taskQueueãšãçŸåšã¢ã¯ãã£ããªã¿ã¹ã¯ã远跡ããrunningTasksã»ãããç¶æããŸãã runTask颿°ã¯ãæå®ãããURLããããŒã¿ãååŸããçµæãyieldãããã¥ãŒã«ããã«URLããããåæå®è¡æ°å¶éã«éããŠããªãå Žåã«æ°ããã¿ã¹ã¯ãéå§ããŸãã- æåã®ã«ãŒãã¯ãåæå®è¡æ°å¶éãŸã§ã®æåã®ã¿ã¹ã¯ã»ãããéå§ããŸãã
main颿°ã¯ã䞊è¡ã€ãã¬ãŒã¿ãŒã䜿çšããŠè€æ°ã®APIããããŒã¿ã䞊åã§åŠçããæ¹æ³ã瀺ããŠããŸããã€ãã¬ãŒã¿ãŒã«ãã£ãŠyieldãããçµæãå埩åŠçããããã«ãfor await...ofã«ãŒãã䜿çšããŸãã
éèŠãªèæ ®äºé ïŒ
- ãšã©ãŒãã³ããªã³ã°ïŒ
runTask颿°ã«ã¯ããã§ããæäœäžã«çºçããå¯èœæ§ã®ããäŸå€ããã£ããããããã®ãšã©ãŒãã³ããªã³ã°ãå«ãŸããŠããŸããæ¬çªç°å¢ã§ã¯ãããå ç¢ãªãšã©ãŒãã³ããªã³ã°ãšãã®ã³ã°ãå®è£ ããå¿ èŠããããŸãã - ã¬ãŒãå¶éïŒ å€éšAPIã䜿çšããå Žåãã¬ãŒãå¶éãå°éããããšãéèŠã§ãããªã¯ãšã¹ãéã«é å»¶ã远å ããããããŒã¯ã³ãã±ããã¢ã«ãŽãªãºã ã䜿çšããããããªã©ããããã®å¶éãè¶ ããªãããã«ããæŠç¥ãå®è£ ããå¿ èŠããããããããŸããã
- ããã¯ãã¬ãã·ã£ãŒïŒ ã€ãã¬ãŒã¿ãŒãã³ã³ã·ã¥ãŒããŒã®åŠçé床ãããéãããŒã¿ãçæããå Žåãã·ã¹ãã ãéè² è·ã«ãªãã®ãé²ãããã«ããã¯ãã¬ãã·ã£ãŒã¡ã«ããºã ãå®è£ ããå¿ èŠããããããããŸããã
䞊è¡ã€ãã¬ãŒã¿ãŒã®å©ç¹
- ããã©ãŒãã³ã¹ã®åäžïŒ éåææäœã®äžŠååŠçã«ãããç¹ã«è€æ°ã®ç¬ç«ããã¿ã¹ã¯ãæ±ãå Žåã«ãå šäœã®å®è¡æéãå€§å¹ ã«ççž®ã§ããŸãã
- å¿çæ§ã®åäžïŒ ã¡ã€ã³ã¹ã¬ããããããã¯ããªãããšã§ã䞊è¡ã€ãã¬ãŒã¿ãŒã¯ã¢ããªã±ãŒã·ã§ã³ã®å¿çæ§ãåäžãããããè¯ããŠãŒã¶ãŒãšã¯ã¹ããªãšã³ã¹ã«ã€ãªãããŸãã
- å¹ççãªãªãœãŒã¹å©çšïŒ 䞊è¡ã€ãã¬ãŒã¿ãŒã䜿çšãããšãI/OæäœãšCPUããŠã³ãã®ã¿ã¹ã¯ããªãŒããŒã©ãããããããšã§ãå©çšå¯èœãªãªãœãŒã¹ãããå¹ççã«æŽ»çšã§ããŸãã
- ã¹ã±ãŒã©ããªãã£ïŒ 䞊è¡ã€ãã¬ãŒã¿ãŒã¯ãã¢ããªã±ãŒã·ã§ã³ãããå€ãã®ãªã¯ãšã¹ããåæã«åŠçã§ããããã«ããããšã§ãã¹ã±ãŒã©ããªãã£ãåäžãããããšãã§ããŸãã
䞊è¡ã€ãã¬ãŒã¿ãŒã®ãŠãŒã¹ã±ãŒã¹
䞊è¡ã€ãã¬ãŒã¿ãŒã¯ã以äžã®ãããªå€æ°ã®ç¬ç«ããéåæã¿ã¹ã¯ãåŠçããå¿ èŠãããã·ããªãªã§ç¹ã«åœ¹ç«ã¡ãŸãã
- ããŒã¿éçŽïŒ è€æ°ã®ãœãŒã¹ïŒAPIãããŒã¿ããŒã¹ãªã©ïŒããããŒã¿ãååŸãããããåäžã®çµæã«çµåãããäŸãã°ãè€æ°ã®eã³ããŒã¹ãã©ãããã©ãŒã ããååæ å ±ãéçŽããããç°ãªãååŒæããéèããŒã¿ãéçŽãããããŸãã
- ç»ååŠçïŒ ãµã€ãºå€æŽããã£ã«ã¿ãªã³ã°ãç°ãªã圢åŒãžã®å€æãªã©ãè€æ°ã®ç»åãåæã«åŠçãããããã¯ç»åç·šéã¢ããªã±ãŒã·ã§ã³ãã³ã³ãã³ã管çã·ã¹ãã ã§äžè¬çã§ãã
- ãã°åæïŒ è€æ°ã®ãã°ãšã³ããªãåæã«åŠçããããšã§ãå€§èŠæš¡ãªãã°ãã¡ã€ã«ãåæãããããã¯ãã¿ãŒã³ãç°åžžããŸãã¯ã»ãã¥ãªãã£ã®è åšãç¹å®ããããã«äœ¿çšã§ããŸãã
- ãŠã§ãã¹ã¯ã¬ã€ãã³ã°ïŒ è€æ°ã®ãŠã§ãããŒãžããåæã«ããŒã¿ãã¹ã¯ã¬ã€ãã³ã°ãããããã¯ç ç©¶ãåæããŸãã¯ç«¶åæ å ±åéã®ããã«ããŒã¿ãåéããããã«äœ¿çšã§ããŸãã
- ãããåŠçïŒ ããŒã¿ããŒã¹ã®ã¬ã³ãŒããæŽæ°ãããã倿°ã®åä¿¡è ã«é»åã¡ãŒã«ãéä¿¡ããããããªã©ãå€§èŠæš¡ãªããŒã¿ã»ããã«å¯ŸããŠãããæäœãå®è¡ããã
ä»ã®äžŠè¡åŠçæè¡ãšã®æ¯èŒ
JavaScriptã¯ãWeb WorkersãPromiseãasync/awaitãªã©ãäžŠè¡æ§ãå®çŸããããã®ããŸããŸãªæè¡ãæäŸããŠããŸãã䞊è¡ã€ãã¬ãŒã¿ãŒã¯ãéåæã¿ã¹ã¯ã®ã·ãŒã±ã³ã¹ãåŠçããã®ã«ç¹ã«é©ããç¹å®ã®ã¢ãããŒããæäŸããŸãã
- Web WorkersïŒ Web Workersã䜿çšãããšãå¥ã®ã¹ã¬ããã§JavaScriptã³ãŒããå®è¡ã§ããCPUéçŽåã®ã¿ã¹ã¯ãã¡ã€ã³ã¹ã¬ããããå®å šã«ãªãããŒãã§ããŸããçã®äžŠåæ§ãæäŸããŸãããã¡ã€ã³ã¹ã¬ãããšã®éä¿¡ãããŒã¿å ±æã«ã¯å¶éããããŸããäžæ¹ã䞊è¡ã€ãã¬ãŒã¿ãŒã¯åãã¹ã¬ããå ã§åäœããäžŠè¡æ§ã®ããã«ã€ãã³ãã«ãŒãã«äŸåããŸãã
- PromiseãšAsync/AwaitïŒ Promiseãšasync/awaitã¯ãJavaScriptã§éåææäœãåŠçããããã®äŸ¿å©ãªæ¹æ³ãæäŸããŸãããããããããã¯æ¬è³ªçã«äžŠåå®è¡ã®ã¡ã«ããºã ãæäŸãããã®ã§ã¯ãããŸããã䞊è¡ã€ãã¬ãŒã¿ãŒã¯ãPromiseãšasync/awaitãåºç€ãšããŠãè€æ°ã®éåæã¿ã¹ã¯ã®äžŠåå®è¡ãç·šæããŸãã
- `p-map`ã`fastq`ã®ãããªã©ã€ãã©ãªïŒ `p-map`ã`fastq`ãªã©ãããã€ãã®ã©ã€ãã©ãªã¯ãéåæã¿ã¹ã¯ã®äžŠè¡å®è¡ã®ããã®ãŠãŒãã£ãªãã£ãæäŸããŸãããããã®ã©ã€ãã©ãªã¯ãããé«ã¬ãã«ã®æœè±¡åãæäŸãã䞊è¡ãã¿ãŒã³ã®å®è£ ãç°¡çŽ åããå ŽåããããŸããç¹å®ã®èŠä»¶ãã³ãŒãã£ã³ã°ã¹ã¿ã€ã«ã«åèŽããå Žåã¯ããããã®ã©ã€ãã©ãªã®äœ¿çšãæ€èšããŠãã ããã
ã°ããŒãã«ãªèæ ®äºé ãšãã¹ããã©ã¯ãã£ã¹
ã°ããŒãã«ãªã³ã³ããã¹ãã§äžŠè¡ã€ãã¬ãŒã¿ãŒãå®è£ ããå Žåãæé©ãªããã©ãŒãã³ã¹ãšä¿¡é Œæ§ã確ä¿ããããã«ãããã€ãã®èŠå ãèæ ®ããããšãäžå¯æ¬ ã§ãã
- ãããã¯ãŒã¯é å»¶ïŒ ãããã¯ãŒã¯é å»¶ã¯ãã¯ã©ã€ã¢ã³ããšãµãŒããŒã®å°ççãªå Žæã«ãã£ãŠå€§ããç°ãªãå¯èœæ§ããããŸããã³ã³ãã³ãããªããªãŒãããã¯ãŒã¯ïŒCDNïŒã䜿çšããŠãç°ãªãå°åã®ãŠãŒã¶ãŒã®é å»¶ãæå°éã«æããããšãæ€èšããŠãã ããã
- APIã¬ãŒãå¶éïŒ APIã«ã¯ãå°åããŠãŒã¶ãŒã°ã«ãŒãããšã«ç°ãªãã¬ãŒãå¶éãããå ŽåããããŸããææ°ããã¯ãªãã®äœ¿çšãå¿çã®ãã£ãã·ã¥ãªã©ãã¬ãŒãå¶éãé©åã«åŠçããæŠç¥ãå®è£ ããŠãã ããã
- ããŒã¿ããŒã«ã©ã€ãŒãŒã·ã§ã³ïŒ ç°ãªãå°åããã®ããŒã¿ãåŠçããŠããå Žåã¯ãããŒã¿ããŒã«ã©ã€ãŒãŒã·ã§ã³ã«é¢ããæ³åŸãèŠå¶ã«æ³šæããŠãã ãããç¹å®ã®å°ççå¢çå ã§ããŒã¿ãä¿åããã³åŠçããå¿ èŠãããå ŽåããããŸãã
- ã¿ã€ã ãŸãŒã³ïŒ ã¿ã€ã ã¹ã¿ã³ããæ±ã£ãããã¿ã¹ã¯ãã¹ã±ãžã¥ãŒã«ãããããéã«ã¯ãç°ãªãã¿ã€ã ãŸãŒã³ã«æ³šæããŠãã ãããä¿¡é Œã§ããã¿ã€ã ãŸãŒã³ã©ã€ãã©ãªã䜿çšããŠãæ£ç¢ºãªèšç®ãšå€æãä¿èšŒããŠãã ããã
- æåãšã³ã³ãŒãã£ã³ã°ïŒ ç¹ã«ç°ãªãèšèªã®ããã¹ãããŒã¿ãåŠçããéã«ã¯ãã³ãŒããç°ãªãæåãšã³ã³ãŒãã£ã³ã°ãæ£ããåŠçããããã«ããŠãã ãããäžè¬çã«ãWebã¢ããªã±ãŒã·ã§ã³ã«ã¯UTF-8ãæšå¥šããããšã³ã³ãŒãã£ã³ã°ã§ãã
- é貚æç®ïŒ éèããŒã¿ãæ±ãå Žåã¯ãæ£ç¢ºãªé貚æç®ã¬ãŒãã䜿çšããããã«ããŠãã ãããææ°ã®æ å ±ãä¿èšŒããããã«ãä¿¡é Œã§ããé貚æç®APIã®äœ¿çšãæ€èšããŠãã ããã
çµè«
JavaScriptã®äžŠè¡ã€ãã¬ãŒã¿ãŒã¯ãã¢ããªã±ãŒã·ã§ã³ã§äžŠååŠçèœåãè§£æŸããããã®åŒ·åãªãã¯ããã¯ãæäŸããŸããJavaScriptã®äžŠè¡æ§ã¢ãã«ã掻çšããããšã§ãããã©ãŒãã³ã¹ãå€§å¹ ã«åäžãããå¿çæ§ãé«ãããªãœãŒã¹å©çšãæé©åã§ããŸããå®è£ ã«ã¯ã¿ã¹ã¯ç®¡çããšã©ãŒãã³ããªã³ã°ãåæå®è¡æ°å¶éã®æ éãªèæ ®ãå¿ èŠã§ãããããã©ãŒãã³ã¹ãšã¹ã±ãŒã©ããªãã£ã®é¢ã§ã®å©ç¹ã¯å€§ãããã®ãšãªãåŸãŸãã
ããè€éã§ããŒã¿éçŽåã®ã¢ããªã±ãŒã·ã§ã³ãéçºããéã«ã¯ãJavaScriptã§ã®éåæããã°ã©ãã³ã°ã®å¯èœæ§ãæå€§éã«åŒãåºãããã«ã䞊è¡ã€ãã¬ãŒã¿ãŒãããŒã«ãããã«çµã¿èŸŒãããšãæ€èšããŠãã ãããäžçäžã®ãŠãŒã¶ãŒã«æé©ãªããã©ãŒãã³ã¹ãšä¿¡é Œæ§ãä¿èšŒããããã«ããããã¯ãŒã¯é å»¶ãAPIã¬ãŒãå¶éãããŒã¿ããŒã«ã©ã€ãŒãŒã·ã§ã³ãªã©ãã¢ããªã±ãŒã·ã§ã³ã®ã°ããŒãã«ãªåŽé¢ãèæ ®ããããšãå¿ããªãã§ãã ããã
ãããªãæ¢æ±
- MDN Web Docsã®éåæã€ãã¬ãŒã¿ãŒãšãžã§ãã¬ãŒã¿ãŒïŒ https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/async_function*
- `p-map`ã©ã€ãã©ãªïŒ https://github.com/sindresorhus/p-map
- `fastq`ã©ã€ãã©ãªïŒ https://github.com/mcollina/fastq