You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node12.x AWS Lambda中try-catch无法捕获Promise拒绝问题咨询

解决AWS Lambda升级Node.js 12.x后TimeoutError无法被try-catch捕获的问题

我之前升级Node.js版本时也碰到过一模一样的问题,这本质是Node.js版本迭代后对Promise未处理拒绝的机制变严格了,加上AWS SDK的Promise行为在新版本下的小变化导致的。

问题根源

在Node.js 8.10中,未处理的Promise拒绝只会触发警告,不会直接终止进程;但从Node.js 10.x开始,未处理的Promise拒绝会被视为致命错误,直接终止运行(包括Lambda函数)。

你的代码里,当你把lambda.invoke(params).promise()推到数组后,这个Promise可能在你还没轮到await它的时候就已经因为超时拒绝了——这时候还没进入try-catch块,所以这个拒绝就变成了“未处理的Promise拒绝”,直接触发Lambda终止。

解决方案

有两种简单有效的处理方式,选哪种都可以:

方式1:提前给每个Promise包装错误捕获

在把Promise加入数组时,就用.catch()捕获所有可能的错误,将Promise转化为永远resolve的状态,返回包含成功/失败标记的对象:

// 修改添加Promise的代码
promiseArray.push(
  lambda.invoke(params).promise()
    .then(result => ({ isSuccess: true, data: result }))
    .catch(error => ({ isSuccess: false, error: error }))
);

然后遍历的时候就不需要try-catch了,直接判断结果:

for (let i = 0; i < promiseArray.length; i++) {
  const result = await promiseArray[i];
  if (result.isSuccess) {
    console.log("Success!");
  } else {
    console.log("Failed!", result.error);
  }
}

方式2:使用Promise.allSettled(Node.js 12.x原生支持)

这个方法会等待所有Promise完成(不管成功还是失败),返回每个Promise的状态结果,完美适配批量处理场景:

// 直接批量处理所有Promise
const results = await Promise.allSettled(promiseArray);

// 遍历结果处理
results.forEach((result, index) => {
  if (result.status === 'fulfilled') {
    console.log(`Promise ${index} Success!`);
  } else {
    console.log(`Promise ${index} Failed!`, result.reason);
  }
});

额外提醒

如果你的Lambda函数还会处理其他Promise,最好全局添加一个未处理拒绝的监听器作为兜底(虽然上面的方案已经能解决问题,但多一层保障更稳妥):

process.on('unhandledRejection', (reason, promise) => {
  console.error('Unhandled Rejection at:', promise, 'reason:', reason);
  // 这里可以添加自定义的兜底处理逻辑
});

内容的提问来源于stack exchange,提问作者spoderman

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 21:27:42