ここでは、.then
でまとめて指定した場合と、どのような違いがでるかについて学んでいきましょう。
次のようなコードを見ていきます。
link:embed/embed-then-throw-error.js[role=include]
// 実行例
badMain(function(){
console.log("BAD");
});
goodMain(function(){
console.log("GOOD");
});
このコード例では、(必ずしも悪いわけではないですが)良くないパターンの badMain
と
ちゃんとエラーハンドリングが行える goodMain
があります。
badMain
がなぜ良くないかというと、.then
の第二引数にはエラー処理を書くことができますが、
そのエラー処理は第一引数の onFulfilled
で指定した関数内で起きたエラーをキャッチすることはできません。
つまり、この場合、 throwError
でエラーがおきても、onRejected
に指定した関数は呼ばれることなく、
どこでエラーが発生したのかわからなくなってしまいます。
それに対して、 goodMain
は throwError
→ onRejected
となるように書かれています。
この場合は throwError
でエラーが発生しても、次のchainである .catch
が呼ばれるため、エラーハンドリングを行うことができます。
.then
のonRejectedが扱う処理は、その(またはそれ以前の)promiseオブジェクトに対してであって、
.then
に書かれたonFulfilledは対象ではないためこのような違いが生まれます。
Note
|
|
この場合の then
は Promise.resolve(42)
に対する処理となり、
onFulfilled
で例外が発生しても、同じ then
で指定された onRejected
はキャッチすることはありません。
この then
で発生した例外をキャッチできるのは、次のchainで書かれた catch
となります。
もちろん .catch
は .then
のエイリアスなので、下記のように .then
を使っても問題はありませんが、
.catch
を使ったほうが意図が明確で分かりやすいでしょう。
Promise.resolve(42).then(throwError).then(null, onRejected);