【问题标题】:grunt testing api with supertest, express and mocha使用 supertest、express 和 mocha 进行 grunt 测试 api
【发布时间】:2015-01-13 21:04:17
【问题描述】:

我有一个由 express 运行的 https 服务器,我使用 mocha 和 supertest 进行测试。

我的问题是 - 如果我只运行测试 - 没关系。如果我尝试使用测试运行 gruntfile 然后运行 ​​express - 我看到很多 EADDRINUSE 错误,即使在测试文件中我使用 app.close() 执行 after()。 同样适用于测试中的 watch 任务。

这是我的示例测试:

/* jshint node: true*/
/*global describe, it, after*/
(function() {
    'use strict';
    process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0";
    var request = require('supertest');
    var app = require('../server.js').app;
    var expect = require('chai').expect;
    var Cookies;

    after(function(done) {
        app.close();
        setTimeout(function(){done();}, 1500);
    });

    describe('/login', function() {
        it('should auth the user', function(done) {
            request(app)
                .post('/login')
                .send({login: "test", password: 'test'})
                .expect(302)
                .end(function(err, res) {
                    expect(err).to.be.equal(null);
                    expect(res.text).to.be.equal("Moved Temporarily. Redirecting to /");
                    Cookies = res.headers['set-cookie'].pop().split(';')[0];
                    done();
            });

        });
    });
    // testing API for serving session data for angualar factory
    describe('/api/session', function() {
        it('should return session data in JSON', function(done) {
            var req = request(app).get('/api/session');             
                req.cookies = Cookies;
                req.set('Accept','application/json')
                .end(function(err, res) {
                    expect(err).to.be.equal(null);
                    expect(res.body).to.have.property("_id");
                    done();
            });
        });
    });

}());

我知道这些测试远非完美。我刚刚通过适当的软件测试开始我的冒险。

所有那些“已经在使用的端口”都是显而易见的,而且它们都没有......给出任何问题。所有测试工作正常,服务器工作正常,但标准输出很疯狂。这种行为远非理想,而且可能充满潜在问题和不稳定问题。

我的问题是 - 如何摆脱它?

我的想法是:

  • 创建专用服务器以仅在不同端口上进行测试。不幸的是,我必须知道如何实现这一点。

  • 如果 superagent 未运行,则为它运行服务器设置一些条件,或者只是...将其传递给 superagent?

  • 使用其他东西然后超级代理(如请求,但我不确定是否所有 cookie 和 node_tls_reject_unauthorized 都可以工作。

如您所见 - 我在这个话题上遇到了困难,问题多于答案,而且经验不足,不知道该去哪里看。

感谢您的帮助。

编辑:

我发现,我可以做到:

before(function(done) {
    app.listen(3001, function() { done(); });
});

在另一个端口上开始测试,但是...整个 server.js 无论如何都会加载,所以它也开始了。然后,当它与运行的服务器一起触发时,有明显的EADDRINUSE。

【问题讨论】:

  • 看不到您的 gruntfile,但您可能正在启动节点应用程序,然后对其进行测试。

标签: node.js unit-testing express mocha.js supertest


【解决方案1】:

当使用superagent 时,您应该始终向其传递一个已配置的 Express 应用程序(已注册中间件、路由控制器等)——但未初始化为 HTTP 服务器。它会为您执行此操作,并将通过http.createServer 推迟到操作系统以选择可用端口。

如果您目前知道server.js 模块已经提供了成熟HTTP 服务器的静态实例,那么这很可能是您的问题的根源。无论哪种情况,请尝试从实际的服务器实例中提取应用程序配置/引导,如下所示:

// server.js
var express = require('express');
var middleware = require('./middleware');
var controllers = require('./controllers');

// Configures the Express application instance.
exports.setup = function (app) {
    app.use(middleware.foo);
    app.get('/bar', controllers.bar);

    app.locals.baz = 'quux';
}

// You might shoot yourself in the foot if parts of your application depend
// on a static reference at `server.app`.
exports.app = setup(express());
exports.app.listen(3000);

然后,在你的测试中,你可以做一些类似的事情:

// tests.js
var express = require('express');
var server = require('./server');

describe('Server tests', function () {
    // Create a fresh server instance prior to each test
    beforeEach(function createNewSever() {
        this.app = server.setup(express());
    });

    describe('Foo', function () {
        it('barrs', function () {
            request(this.app)  // initializes a server instance on port A
            // ... supertests
        });

        it('bazzes', function () {
            request(this.app)  // initializes a server instance on port B
            // ... more supertests
        });
    });
});

这仅用于说明目的,实例化应用程序实例的时间/方式将取决于您的测试上下文。要带走的重要一点是,您应该能够为您的测试用例创建新鲜、干净、独立和隔离的服务器实例。如果您使用并行或随机顺序执行测试的测试运行器,这是绝对必要的。

【讨论】:

  • server.js 实际上启动服务器以侦听端口 3000 是否没有问题。将 setup 功能放在单独的模块中不是更好吗?
猜你喜欢
  • 2016-06-05
  • 1970-01-01
  • 2015-03-03
  • 1970-01-01
  • 2017-11-29
  • 1970-01-01
  • 2021-08-15
  • 2023-04-09
  • 2013-01-23
相关资源
最近更新 更多