Promise
は次のサンプルコードように、失敗したらreject
を、成功したらresolve
を呼び出すような書き方をする。
new Promise((resolve, reject) => {
// ...
if (err) {
reject(err)
} else {
resolve()
}
})
このサンプルコードは、正常系と異常系でif分岐されており、resolve
とreject
が両方呼ばれる可能性はない。
もしも、resolve
とreject
の両方を呼び出したらどうなるのだろうか?
new Promise((resolve, reject) => {
reject()
resolve()
})
普通はこんなことはしないだろうが、Promise
の仕様を知っておくのは良さそうだ。
実験1: resolve
→reject
の順で呼んでみる
実験してみよう。まずは、resolve
→reject
の順で呼び出してみよう。
new Promise((resolve, reject) => {
resolve()
reject()
}).then(value => console.log('success'))
.catch(reason => console.log('failure'))
//=> success
この実行結果は、「success」になり、resolve
が尊重されたかたちになった。
実験2: reject
→resolve
の順で呼んでみる
今度は逆に、reject
のほうを先に呼び出してみることにする。
new Promise((resolve, reject) => {
reject()
resolve()
}).then(value => console.log('success'))
.catch(reason => console.log('failure'))
//=> failure
今度の結果は「failure」になった。reject
のほうが採用されたことが分かる。
結論: 先に呼ばれたほうが採用される
「Promiseのresolve
とreject
の両方を呼び出したらどうなってしまうのか?」の疑問への答えとしては、「先に呼ばれたほうが採用される」ということになりそうだ。
余談: 先勝ちと言っても、処理が中断されるわけではない
ちなみに、resolve
とreject
どちらかが採用されるとは言え、Promise
に渡したexecuterの処理が中断されるわけではない。例えば、下記のコードでは、①でresolve
が採用されるが、そのあとの②③の行も実行される。
new Promise((resolve, reject) => {
resolve() // ①
console.log('after resolve') // ②
reject() // ③
}).then(value => console.log('success'))