Promise Error Handling
+約束されたエラー
++
Promiseとエラーの基本
+-
+
- Promise内で起きた例外は自動でキャッチされる +
- エラー処理は
.catch(fn)
で行う
+
var promise = new Promise(function(){
+ throw new Error("例外");
+});
+promise.catch(function(error){
+ // 例外をキャッチできる
+});
+
++
よくある問題
+-
+
.catch(fn)
をしないとエラーログも出せない
+.catch(fn)
をしわすれてエラーの握りつぶしが起きる
+- = unhandled rejection (
.catch
をしてないpromise)
+ - 4.6. Promise.prototype.done とは何か? +
+
現状のunhandled rejectionへの対応
+-
+
- unhandled rejectionが発生した時にコンソールに出すかは実装依存 +
- FirefoxはGCのタイミング +
- Chromeは開発者ツールが有効の場合 + +
- bluebirdやypromiseはコンソールへ出す +
- Node.jsは何も言わない? +
+
今日のテーマ: unhandledRejection
+-
+
- unhandled rejectionは予期せぬ出来事 +
- 少なくてもエラーのログは取りたい
-
+
Promise.prototype.done
を実装するのは本質的ではない
+
+ 'unhandledRejection'
,'rejectionHandled'
というイベントの実装が進められているという話
+- ECMAScript 6の仕様ではありません +
+
unhandledRejection / rejectionHandled
+bluebirdが主導してるの例はbluebird
++
unhandledRejection イベント
+var bluebird = require("bluebird");
+process.on("unhandledRejection", function (reason, promise) {
+ console.log("unhandledRejection");
+});
+
+var resolved = bluebird.resolve();
+resolved.then(function () {
+ throw new Error("Yay!");
+});
+
++
unhandledRejection イベント
+-
+
catch
してないPromiseでエラーが発生すると発行されるイベント
+.catch
してないpromiseオブジェクトを見つけるのを助ける
+window.onerror
みたいなもの
+
process.on("unhandledRejection", function (reason, promise) {
+ // エラー理由とpromiseがやってくる
+});
+
++
rejectionHandled イベント
+var Promise = require("bluebird");
+process.on("rejectionHandled", function (promise) {
+ console.log("rejectionHandled");
+});
+var rejected = Promise.reject(new Error("Error Promise"));
+setTimeout(function () {
+ rejected.catch(function () {
+ // rejected済みのpromiseに`catch`する
+ });
+},100);
+
++
rejectionHandled イベント
+-
+
- rejected済みのpromiseに
catch
した時に起きるイベント
+ - 呼ばれることがない
catch
の発見に役立つ
+
+
実際の使い方
+-
+
- unhandledRejectionのログを取りたい場合 +
var unhandledRejections = new Set();
+process.on('unhandledRejection', function(reason, p) {
+ unhandledRejections.add(p);
+});
+process.on('rejectionHandled', function(p) {
+ unhandledRejections.delete(p);
+});
+
++
unhandledRejection & rejectionHandled
+-
+
- なぜ
unhandledRejection
だけ欲しいのにrejectionHandled
も見るの?
+ - =>
rejectionHandled
が起きるケースはunhandledRejection
が先に起きてる事がある
+
+
unhandledRejection & rejectionHandledパータン
+var rejected = Promise.reject();
+setTimeout(()=>{
+ // 2. rejectionHandledイベント
+ rejected.catch(()=>{});
+}, 100);
+// 1. unhandledRejectionイベント
+
++
unhandledRejection & rejectionHandled
+-
+
- unhandledRejection と rejectionHandled は基本セットで使う +
- rejectionHandled単体の使い道はあんまりなさそう? +
+
使い方とドキュメント
+参考資料
+-
+
- process io.js Manual & Documentation +
- Promise unhandled rejection tracking global handler hook +
- Global rejection events - bluebird +
+
実装
++
ことのはじまり
+-
+
- bluebirdの実装提案 + +
- @benjamingrさんが色々利用状況を調べてプロポーサルを書いた +
- Promise unhandled rejection tracking global handler hook +
+
ライブラリの実装
+-
+
- bluebird v2.7.0で実装 +
- when.js v3.7.0で実装 +
- io.js v1.4.1で実装 by @petkaantonov + +
+
小さいプロポーサルからの実装
+-
+
- Promise/A+の頃から同じような話はあった + +
- DOM/ECMAScript Promiseでも話があった程度 + +
+
Implementation in userland
+++Implementation in userland +-- Consider exposing promise unhandled rejection hook · Issue #256 · iojs/io.js
+
+
Implementation in userland
+-
+
- ユーザランドでの実装から始まっている面白い動き
-
+
- Promise自体もコミュニティ仕様からECMAScript仕様に入った +
+ - io.js にも入ったため、他のPromiseライブラリにも実装が進んでいきそうな空気がある
-
+
- コミュニティ標準から仕様へ? +
+
+
まとめ
+-
+
- Promiseでエラーの握りつぶしがよく起きてる +
- 現状ではunhandled rejectionの扱いは実装依存 +
- unhandled rejectionが起きた時に発行するイベントを定義したコミュニティプロポーサルがでた +
- bluebirdやio.jsなどで実装された +
- ECMAScript仕様の話はまだない +