首页 > 解决方案 > 使用 forEach 循环处理 mongoose 的错误

问题描述

我有一个带有 express 的 mongodb,Cannot set headers after they are sent to the client. Unhandled promise rejections are deprecated在执行以下操作时出现错误。

exports.deleteBooking = (req, res, next) => {
  req.body.courts.forEach(element => {
    Booking.deleteOne({$and: [
      { cid: element.cid },
      { year: element.day.year }
    ]})
    .then(result => {
      res.status(201).json({
        message: result
      });
    })
    .catch(() => {
      res.status(500).json({
        error: 'error'
      })
    });
  })
};

我正在向我的服务器发送一组对象,并希望对每个对象执行一次删除。

因为forEach它可能会在标头发送到客户端后运行 .catch。使用 forEach 循环.then的正确处理方法是什么?.catch

谢谢!

编辑:我忘了补充一点,如果我删除.then并且.catch查询仍然会运行,并且没有错误。但我想在这种情况下保留错误处理。

标签: node.jsmongodbmongodb-query

解决方案


res.status(201).json是在forEach循环中,因此为什么会出现上述错误:您只能发送一次数据。

要解决这个问题,您基本上需要发送deleteOne一次操作并使用bulkWrite()它,因为它允许您在一个命令中向 MongoDB 服务器发送多个 deleteOne 操作。它以对象数组的形式接受输入,如下所示

Booking.bulkWrite([
    { deleteOne: { filter: { cid: 1, year: 2007 } } },
    { deleteOne: { filter: { cid: 2, year: 2007 } } },
    { deleteOne: { filter: { cid: 3, year: 2007 } } },
    { deleteOne: { filter: { cid: 4, year: 2007 } } }, 
])

因此,在您的情况下,您可以将req.body.courts数组映射到上述deleteOne操作

exports.deleteBooking = (req, res, next) => {
    Booking.bulkWrite(
        req.body.courts.map(({ cid, day }) => ({
            deleteOne: { filter: { cid, year: day.year } }
        }))
    ).then(message => {
        res.status(201).json({ message })
    }).catch(error => {
        res.status(500).json({ error })
    })
}

推荐阅读