我正在尝试使用nodeunit测试我的Web服务器:
test.js
exports.basic = testCase({
setUp: function (callback) {
this.ws = new WrappedServer();
this.ws.run(PORT);
callback();
},
tearDown: function (callback) {
delete this.ws;
callback();
},
testFoo: function(test) {
var socket = ioClient.connect(URL);
console.log('before client emit')
socket.emit('INIT', 1, 1);
console.log('after client emit');
}
});
这是我非常简单的nodejs服务器:
WrappedServer.prototype.run = function(port) {
this.server = io.listen(port, {'log level': 2});
this.attachCallbacks();
};
WrappedServer.prototype.attachCallbacks = function() {
var ws = this;
ws.server.sockets.on('connection', function(socket) {
ws.attachDebugToSocket(socket);
console.log('socket attaching INIT');
socket.on('INIT', function(userId, roomId) {
// do something here
});
console.log('socket finished attaching INIT');
});
}
基本上我收到了这个错误:
[...cts/lolol/nodejs/testing](testingServer)$ nodeunit ws.js
info - socket.io started
before client emit
after client emit
info - handshake authorized 1013616781193777373
The "sys" module is now called "util". It should have a similar interface.
socket before attaching INIT
socket finished attaching INIT
info - transport end
不知何故,套接字在服务器附加套接字回调之前发出INIT。
为什么会这样?另外,正确的方法是什么?
答案 0 :(得分:0)
我假设您期望订单是这样的?
从给出的少量代码中,问题可能是两件事。
首先,也许主要问题是你的ioClient.connect不会立即连接。您需要将某种回调传递给它,并发出INIT
,然后在实际连接后执行测试的callback
函数。
其次,您可能应该使用run
命令执行相同的操作。 listen
不会立即停止监听,因此如果在执行测试时尚未开始监听,您偶尔会得到不一致的结果。您还应该将setUp的callback
传递给io.listen
。
<强>更新强>
要明确listen
,就像节点中的大多数事情一样,socketio服务器的listen
方法是异步的。调用该方法告诉它开始监听,但是在后台有一段时间服务器设置网络内容以开始监听。就像节点的核心listen
,http://nodejs.org/docs/latest/api/net.html#server.listen一样,socket.io的版本采用一个在服务器启动和监听后调用的回调参数。
io.listen(port, {'log level': 2}, callback);
除非socket.io开始为您提供有关无法连接的错误,否则这可能不是问题,但需要牢记这一点。将异步操作视为瞬时操作是一种简单的方法,可以使错误偶尔出现。由于你的run
包裹听,我认为一般而言,不仅仅是测试,将回调传递给run
将是一个非常好的主意。