27

bluebird Promise ライブラリを使用しています。promise をチェーンして、特定の promise エラーをキャッチしたいと思います。これが私がやっていることです:

getSession(sessionId)
  .catch(function (err) {
    next(new Error('session not found'));
  })
  .then(function (session) {
    return getUser(session.user_id);
  })
  .catch(function (err) {
    next(new Error('user not found'));
  })
  .then(function (user) {
    req.user = user;
    next();
  });

しかし、 によってエラーがスローされた場合、 2 番目の と同様にgetSession2 つが呼び出されます。最初の でエラーの伝播を停止したいので、2 番目はスローされたときにのみ呼び出され、2 番目は成功したときに呼び出されます。どうする?catchthencatchcatchgetUserthengetUser

4

3 に答える 3

23

メソッドによって返される promise は.catch、コールバックの結果で引き続き解決されます。これは、チェーンの伝播を停止するだけではありません。チェーンを分岐する必要があります。

var session = getSession(sessionId);
session.catch(function (err) { next(new Error('session not found')); });
var user = session.get("user_id").then(getUser);
user.catch(function (err) { next(new Error('user not found')); })
user.then(function (user) {
    req.user = user;
    next();
});

または 2 番目のコールバックを使用してthen:

getSession(sessionId).then(function(session) {
    getUser(session.user_id).then(function (user) {
        req.user = user;
        next();
    }, function (err) {
        next(new Error('user not found'));
    });
}, function (err) {
    next(new Error('session not found'));
});

別の方法として、エラーをチェーン全体に伝播させ、next最後にのみ呼び出す方法をお勧めします。

getSession(sessionId).catch(function (err) {
    throw new Error('session not found'));
}).then(function(session) {
    return getUser(session.user_id).catch(function (err) {
        throw new Error('user not found'));
    })
}).then(function (user) {
    req.user = user;
    return null;
}).then(next, next);
于 2014-07-07T20:58:43.663 に答える
7

プロミスにブルーバードを使用しているため、実際にはすべての関数の後に catch ステートメントは必要ありません。すべての then を連鎖させて、1 回のキャッチで全体を閉じることができます。このようなもの:

getSession(sessionId)
  .then(function (session) {
    return getUser(session.user_id);
  })
  .then(function (user) {
    req.user = user;
    next();
  })
  .catch(function(error){
    /* potentially some code for generating an error specific message here */
    next(error);
  });

エラーメッセージがエラーの内容を示していると仮定すると、「セッションが見つかりません」や「ユーザーが見つかりません」などのエラー固有のメッセージを送信することは可能ですが、エラーメッセージを調べて何が表示されるかを確認する必要がありますあなた。

注: エラーがあるかどうかに関係なく、おそらく next を呼び出す理由があると思いますが、エラーが発生した場合に console.error(error) をスローすると役立つ場合があります。あるいは、console.error や res.send(404) など、他のエラー処理関数を使用することもできます。

于 2014-07-07T21:07:22.250 に答える