Could anyone provide a rock-solid, dead-simple unit test for Node.js using WebSockets (Socket.io)?
I'm using socket.io for Node.js, and have looked at socket.io-client for establishing the client connection to a server in the test. However, I seem to be missing something.
In the example below, "worked..." never gets printed out.
var io = require('socket.io-client') , assert = require('assert') , expect = require('expect.js'); describe('Suite of unit tests', function() { describe('First (hopefully useful) test', function() { var socket = io.connect('http://localhost:3001'); socket.on('connect', function(done) { console.log('worked...'); done(); }); it('Doing some things with indexOf()', function() { expect([1, 2, 3].indexOf(5)).to.be.equal(-1); expect([1, 2, 3].indexOf(0)).to.be.equal(-1); }); }); });
Instead, I simply get:
Suite of unit tests First (hopefully useful) test ✓ Doing some things with indexOf() 1 test complete (26 ms)
Any suggestions?
Node. js can maintain many hundreds of WebSockets connections simultaneously. WebSockets on the server can become complicated as the connection upgrade from HTTP to WebSockets requires handling. This is why developers commonly use a library to manage this for them.
First of all, every modern browser supports WebSockets these days. Socket.IO uses much more boilerplate code and resources to make it fall back to other technologies. Most of the time, you don't need this level of support. Even in terms of network traffic, Socket.IO is way more expensive.
You can check the socket. connected property: var socket = io. connect(); console.
In order to do it, you need to create an index. js file and install socket.io and express. You can use the following command: touch index. js && npm install express socket.io && npm install --save-dev nodemon .
After further poking and prodding, I found some incredibly useful information. In the author's example, he points out the critical step of establishing socket listeners in the before
hooks.
This example works:
Assuming a server is listening for socket connections at
localhost:3001
, of course
var io = require('socket.io-client') , assert = require('assert') , expect = require('expect.js'); describe('Suite of unit tests', function() { var socket; beforeEach(function(done) { // Setup socket = io.connect('http://localhost:3001', { 'reconnection delay' : 0 , 'reopen delay' : 0 , 'force new connection' : true }); socket.on('connect', function() { console.log('worked...'); done(); }); socket.on('disconnect', function() { console.log('disconnected...'); }) }); afterEach(function(done) { // Cleanup if(socket.connected) { console.log('disconnecting...'); socket.disconnect(); } else { // There will not be a connection unless you have done() in beforeEach, socket.on('connect'...) console.log('no connection to break...'); } done(); }); describe('First (hopefully useful) test', function() { it('Doing some things with indexOf()', function(done) { expect([1, 2, 3].indexOf(5)).to.be.equal(-1); expect([1, 2, 3].indexOf(0)).to.be.equal(-1); done(); }); it('Doing something else with indexOf()', function(done) { expect([1, 2, 3].indexOf(5)).to.be.equal(-1); expect([1, 2, 3].indexOf(0)).to.be.equal(-1); done(); }); }); });
I found that the placement of done()
in the beforeEach
, socket.on('connect'...)
listener was crucial to having the connection get established. For example, if you comment out done()
in the listener, then add it one scope out (just before exiting the beforeEach
), you'll see the "no connection to break..." message instead of the "disconnecting..." message. Like so:
beforeEach(function(done) { // Setup socket = io.connect('http://localhost:3001', { 'reconnection delay' : 0 , 'reopen delay' : 0 , 'force new connection' : true }); socket.on('connect', function() { console.log('worked...'); //done(); }); socket.on('disconnect', function() { console.log('disconnected...'); }); done(); });
I'm new to Mocha, so there's probably a very obvious reason to the initiated for placing done()
within the socket scope itself. Hopefully that little detail will save others in my shoes from hair pulling.
For me, the above test (with correct scoping of done()
) outputs:
Suite of unit tests First (hopefully useful) test ◦ Doing some things with indexOf(): worked... ✓ Doing some things with indexOf() disconnecting... disconnected... ◦ Doing something else with indexOf(): worked... ✓ Doing something else with indexOf() disconnecting... disconnected... 2 tests complete (93 ms)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With