gpt4 book ai didi

javascript - 处理 promise 链中的多个捕获

转载 作者:IT老高 更新时间:2023-10-28 21:46:55 32 4
gpt4 key购买 nike

我对 promises 还很陌生,目前正在使用 bluebird,但是我有一个场景,我不太确定如何最好地处理它。

例如,我在一个 express 应用程序中有一个 promise 链,如下所示:

repository.Query(getAccountByIdQuery)
.catch(function(error){
res.status(404).send({ error: "No account found with this Id" });
})
.then(convertDocumentToModel)
.then(verifyOldPassword)
.catch(function(error) {
res.status(406).send({ OldPassword: error });
})
.then(changePassword)
.then(function(){
res.status(200).send();
})
.catch(function(error){
console.log(error);
res.status(500).send({ error: "Unable to change password" });
});

所以我追求的行为是:

  • 通过 Id 获取帐号
  • 如果此时出现拒绝,则轰炸并返回错误
  • 如果没有错误将返回的文档转换为模型
  • 用数据库文档验证密码
  • 如果密码不匹配,则弹出并返回不同的错误
  • 如果没有错误,请更改密码
  • 然后返回成功
  • 如果还有其他问题,请返回 500

所以目前的捕获似乎并没有停止链接,这是有道理的,所以我想知道是否有办法让我根据错误以某种方式强制链在某个点停止,或者是否有一种更好的方式来构造它以获得某种形式的分支行为,因为有 if X do Y else Z 的情况。

任何帮助都会很棒。

最佳答案

此行为与同步抛出完全相同:

try{
throw new Error();
} catch(e){
// handle
}
// this code will run, since you recovered from the error!

这是 .catch 的一半——能够从错误中恢复。可能需要重新抛出以表明状态仍然是错误:

try{
throw new Error();
} catch(e){
// handle
throw e; // or a wrapper over e so we know it wasn't handled
}
// this code will not run

但是,仅此一项不适用于您的情况,因为错误会被稍后的处理程序捕获。这里真正的问题是通用的“处理任何事情”错误处理程序通常是一种不好的做法,并且在其他编程语言和生态系统中非常不受欢迎。出于这个原因,Bluebird 提供了类型化和谓词捕获。

额外的好处是您的业务逻辑根本不需要(也不应该)了解请求/响应周期。决定客户端获取哪种 HTTP 状态和错误不是查询的责任,随着应用程序的增长,您可能希望将业务逻辑(如何查询数据库以及如何处理数据)与发送给客户端的内容分开(什么http状态码,什么文本,什么响应)。

我会这样写你的代码。

首先,我会让 .Query 抛出一个 NoSuchAccountError,我会从 Bluebird 已经提供的 Promise.OperationalError 继承它.如果您不确定如何对错误进行子类化,请告诉我。

我还会为 AuthenticationError 附加子类,然后执行以下操作:

function changePassword(queryDataEtc){ 
return repository.Query(getAccountByIdQuery)
.then(convertDocumentToModel)
.then(verifyOldPassword)
.then(changePassword);
}

如您所见 - 它非常干净,您可以像阅读说明手册一样阅读文本,了解过程中发生的情况。它也与请求/响应分开。

现在,我将从路由处理程序中调用它:

 changePassword(params)
.catch(NoSuchAccountError, function(e){
res.status(404).send({ error: "No account found with this Id" });
}).catch(AuthenticationError, function(e){
res.status(406).send({ OldPassword: error });
}).error(function(e){ // catches any remaining operational errors
res.status(500).send({ error: "Unable to change password" });
}).catch(function(e){
res.status(500).send({ error: "Unknown internal server error" });
});

这样,逻辑都在一个地方,如何向客户端处理错误的决定都在一个地方,它们不会相互混淆。

关于javascript - 处理 promise 链中的多个捕获,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26076511/

32 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com