[失敗] Promise.allを順序じゃなく「意味」で束ねた ― keyedPromiseAll
経緯
Promise.all って、タプルの順序が変わらないことを前提に作られていて
それ自体は言語仕様だし悪いことじゃないんだけど、自分にとってはちょっと気持ち悪かった。
なので、順序ではなく、処理に意味(key)を持たせて応答と紐づける仕組みを作ってみた。
仕組みの話
全体の構成としては
namespace keyedPromiseAll
promiseAll ... Promise配列を受け取って、待ってから返す
promiseAllWithArgs ... 関数と引数の配列を受け取って、待ってから返す
この2種類を作成した。
なるべく型安全に作ったのだけど、どうしてもPromise<any>を消しきれない部分
(正確には、L69 の fn が、どんなに頑張っても関数定義のTの制約に引きづられる)
があるので、完成かと言うとちょっと微妙なのだけど、仕組みで整合性は確保してる。
一部簡単なUtilityも付け加えたけど、もう少し使いやすくする予定で、
それは別枠で扱おうかなと思っている
コード
扱う型の定義
全体てみるともう少し、関数内の定義もあるけど、おおよそはここに集約。
引数に渡された構造から、keyの構造を崩さずに、いろんな箇所の型を抜き出すことをしてる。
「抜き出してる!」って感じがする代表格は ArgsMap かなぁ。
関数が引数で渡ってくるので、そのパラメータを引き出す感じ。
ちなみに、タプルのKeyを崩さずに、異る型に違う抜き出しを書けるみたいな書き方は、わからかったので、ChatGPTに聞いたら、「こうするとできるぞ」って一瞬で出してきて、悩んだ俺がアホみたいだw
知らないことがまだまだ多すぎるね。
PromiseAll
Promise配列をうけとって待ってくれる、元の Promise.all に似た動き
処理的には、受け取ったPromiseの配列をPromiseAllでまたせるんだけど、このときに
Keyの部分を崩さないように処理してる。
結果を書き戻すときに、Keyを基準にいれていくことで、それぞれの結果がそれぞれの名前で保持される。成功失敗に関しては、Promiseの単位でみていて、rejectされた場合とかは、okがfalseになって、errorがセットされる仕組み
PromiseAllWithArg
関数と引数の配列をうけとって、中で実行までしてくれる PromiseAll 受け取った内容の実行をかけてから、Promiseの結果を集めて返してくれる仕組みです。
handleResult
結果がだいぶ見づらいので、ヘルパー関数を用意してみました
実行部分
ここからは実行部分です。
関数をタプルに詰め込んで送り込むと、結果が返却されてきます。
Discussion