【问题标题】:Express.js - Cannot Set Headers with exported functionExpress.js - 无法使用导出函数设置标题
【发布时间】:2020-09-12 02:07:14
【问题描述】:

学习如何使用 MochaChaiChai-HTTP 插件和 MongoDB进行 Express 测试> 与猫鼬。我有一个测试来故意检测 MongoDB 是否会在尝试使用错误的 _id 值(太短)查找文档时发回错误。

我注意到我的部分代码在我的其他 Express 路线周围重复,并希望将其重用于其他路线,所以我从另一个模块导出它,但现在我得到了:

Uncaught Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client

不知道为什么我会收到此错误。如果我有与导出函数相同的代码,在路由代码中它工作正常,但导出它只是抱怨。

代码如下:

test/route/example.test.js Snippit

it('Bad request with a too short ID string (12 characters minimum)', () => {
    // /api/v1/example is the endpoint
    // /blah is the param
    chai.request(app).get('/api/v1/example/blah').end((err, res) => {
       // Insert all the nice assert stuff. :) 
    });
});

route/example.js片段

// Packages
const router = require('express').Router();

// Models (Mongoose Schemas)
const Example = require('../models/example.model');

// Helpers
const { foundMongoError } = require('../helpers/routes');

// -----Snipped-----

router.route('/:exampleId').get((req, res) => {
    // Retrieve the exampleId parameter.
    const exampleId = req.params.exampleId;

    Example.findById(exampleId, (mongoError, mongoResponse) => {
        foundMongoError(mongoError, res); // Having an issue

        // If I have the same code that makes up foundMongoError inside here, no issues, 
        // but it will no longer be DRY.

        // Check if any responses from MongoDB
        if(mongoResponse) {
            res.status(200).json(mongoResponse);
        } else {
            return res.status(404).json({
                errorCode: 404,
                errorCodeMessage: 'Not Found',
                errorMessage: `Unable to find example with id: ${exampleId}.`
            });
        }
    });
});

helpers/routes.js

const foundMongoError = (mongoError, res) => {
    if(mongoError) {
        return res.status(400).json({
            errorCode: 400,
            errorCodeMessage: 'Bad Request',
            errorMessage: mongoError.message
        });
    }
};

module.exports = {
    foundMongoError
};

【问题讨论】:

    标签: javascript node.js express mongoose mocha.js


    【解决方案1】:

    这意味着您发送并回复res 两次。第一次发回这里:

        if(mongoError) {
            return res.status(400).json({
                errorCode: 400,
                errorCodeMessage: 'Bad Request',
                errorMessage: mongoError.message
            });
        }
    

    您发回了响应,但该函数仍在继续工作,这意味着该函数将一直运行到此处:

        if(mongoResponse) {
            res.status(200).json(mongoResponse);
        } else {
            return res.status(404).json({
                errorCode: 404,
                errorCodeMessage: 'Not Found',
                errorMessage: `Unable to find example with id: ${exampleId}.`
            });
        }
    

    这里发生了第二个响应,在这里你得到了错误。

    我会这样重写代码:

    你返回一个true而不是返回响应,这意味着有一个错误,否则false

    const foundMongoError = (mongoError, res) => {
        if(mongoError) {
            res.status(400).json({
                errorCode: 400,
                errorCodeMessage: 'Bad Request',
                errorMessage: mongoError.message
            });
        return true;
        }
        return false;
    };
    
    module.exports = {
        foundMongoError
    };
    

    那么你可以这样写:

    if(foundMongoError(mongoError, res)) return;
    

    return 将停止函数以执行其余代码

    【讨论】:

    • 输入这个问题几秒钟后,我意识到我需要从路由文件中返回响应,但我更喜欢你的方法而不是我想要做的。谢谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-09-06
    • 2018-02-26
    • 2020-12-24
    • 1970-01-01
    • 2015-08-10
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多