node.jshttptestingmocha.jsnode.js-connect

http-request testing of nodejs (connect) apps with mocha?


I want to write some integration-tests for my connect-middleware and test it with real-http-requests instead of mocked requests.

The middleware stack behaves differently depending on the configuration passed, that's why i wanted to run the middleware-server as a subprocess which i can restart with different configuration after each test.

The problem is that the test-server runs without problems (ether started directly or within test-file) and is accessible via browser, but i don't get a response via http.get(..) because the connection is refused.

Error: connect ECONNREFUSED

Here is my Setup...

//MOCHA TEST FILE: testServer.test.js

function runTestServer(configEnv) {

    var cmd = "node " + path.resolve(__dirname, "runTestServer.js");

    var testSrv = exec(cmd, { "env" : configEnv },
    function (error, stdout, stderr) {
        if (error !== null) {
            console.log('exec error: ' + error);
        }
    });

    return testSrv;
}


describe("onRequest", function(){
    it("should return a response", function (done) {

        this.timeout(100000);

        var serverInstance = runTestServer({
            "appDir" : path.resolve(__dirname, "../../handleHttp/app")
        });

        http.get({host:'localhost', port:9090, path:'/'}, function (res) {
            //error thrown before this callback gets called
        });

    });
});

That's the content of my testServer.js file which runs as a subprocess.

//Test-Process-File: runTestServer.js
var connect = require("connect"),
handleHttp = require("...")

var server = connect();
handleHttp.init(server); //this methods applies the middleware
console.log("TEST-SERVER listening on 9090");
server.listen(9090);

Solution

  • I figured this one out while posting the questions and want to answer it here, in case someone else is having the same kind of problem.

    So what's the problem?

    The whole thing is async!

    So the server won't be initialized before the requests are being fired to the server.

    Solution

    Give the subprocess some time to initialize and make the testServer-Loader Async!

    function runTestServer(configEnv, callback) {
    
        var cmd = "node " + path.resolve(__dirname, "../runTestServer.js"),
        testSrv;
    
        testSrv = exec(cmd, { "env" : configEnv },
                     function (error, stdout, stderr) {
                       if (error !== null) {
                         console.log('exec error: ' + error);
                      }
                  });
    
        setTimeout(function() {
            callback(testSrv);
        }, 1000);
    }
    

    My mocha-test-file:

    describe("handleHttp", function() {
      describe("#Basic Requesting", function() {
    
        var serverInstance;
    
        before(function(done) {
            runTestServer({
                "appDir" : path.resolve(__dirname, "...")
            }, function(srvInstance) {
                serverInstance = srvInstance;
                done();
            });
        });
    
        //run your tests here 
    

    The fixed timeout is not really a nice solution. Maybe it's possible to enable some communication between the main and subprocess in order to find out when the http-server is ready. Suggestions appreciated.