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

NodeJs/Express/MongoDb PUT请求触发ERR_HTTP_HEADERS_SENT错误求助

问题根因
  • 核心错误点:findOneAndUpdate 同时使用 await 异步语法和回调函数,导致同一条查询被Mongoose执行两次:
    1. 第一次执行触发回调,在回调内已经调用res.send()返回响应给客户端
    2. 第二次执行尝试再次返回响应,触发Cannot set headers after they are sent to the client错误,同时抛出Query was already executed的查询重复执行异常
  • 次要问题1:UserModel.remove 是已弃用的API,会触发驱动警告,需要替换为deleteOne
  • 次要问题2:userInfo接口查询出错时仅打印日志,没有返回响应,会导致客户端超时
修正方案

直接统一使用async/await语法处理所有数据库操作,移除回调函数即可:

const UserModel = require("../models/user.model");
const ObjectID = require("mongoose").Types.ObjectId;

module.exports.getAllUsers = async (req, res) => {
  try {
    const users = await UserModel.find().select("-password");
    res.status(200).json(users);
  } catch (err) {
    res.status(500).json({ message: err });
  }
};

module.exports.userInfo = async (req, res) => {
  if (!ObjectID.isValid(req.params.id))
    return res.status(400).send("ID unknown : " + req.params.id);
  try {
    const user = await UserModel.findById(req.params.id).select("-password");
    res.send(user);
  } catch (err) {
    console.log("Id unknown" + err);
    res.status(500).send("Id unknown" + err);
  }
};

module.exports.updateUser = async (req, res) => {
  if (!ObjectID.isValid(req.params.id))
    return res.status(400).send("ID unknown : " + req.params.id);
  try {
    const updatedUser = await UserModel.findOneAndUpdate(
      { _id: req.params.id },
      { $set: { bio: req.body.bio } },
      { new: true, upsert: true, setDefaultsOnInsert: true }
    );
    res.send(updatedUser);
  } catch (err) {
    return res.status(500).json({ message: err });
  }
};

module.exports.deleteUser = async (req, res) => {
  if (!ObjectID.isValid(req.params.id))
    return res.status(400).send("ID unknown : " + req.params.id);
  try {
    // 替换弃用的remove为deleteOne
    await UserModel.deleteOne({ _id: req.params.id });
    res.status(200).json({ message: "Successfully deleted. " });
  } catch (err) {
    return res.status(500).json({ message: err });
  }
};
验证

修改完成后调用PUT更新接口,数据库更新正常,不会再抛出重复查询和响应头重复设置的错误。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.04 20:30:01