10
votes

I'm trying to hook in socket.io to a Hapi.js server. I've tested the socket.io implementation in vanilla Node.js and everything works great; the server side of the Hapi implementation seems to work fine, but the "/socket.io/socket.io.js" resource is not served to the client.

I've checked the Hapi example, but they only show what to do on the server, and their documentation on the client handshake seems odd: they have a server on port 8000 but say to post for the socket.io handshake to 8080--I've even tried this (which seems wonky and inconsistent with every other socket.io implementation) with no luck.

Thanks!

4
+1 for the hapi example - Dmitry Minkovsky

4 Answers

3
votes

Hapi 8 has introduced some new intricacies so if anyone if revisiting this issue...

On the client, you don't have to use /socket.io/socket.io.js, instead use

  1. a cdn (https://cdnjs.cloudflare.com/ajax/libs/socket.io/0.9.16/socket.io.min.js)
  2. or serve the file more specifically (http://yoursite.io/js/socket.io/socket.io.js)
  3. Better yet, use something like npm/browserify and (https://www.npmjs.com/package/socket.io-client):

    var socket = require('socket.io-client')('http://localhost:8080');

Which ever way you choose to include the client side code above

Hapi 8 will allow you to do something cool on your server with chat like this:

server.js

server.connection({ port: 8000, labels: 'app' });
server.connection({ port: 8080, labels: 'chat' });
server.register({
    register: require('./server/plugins/socketIO')
}, 
function(err) {
    if (err) throw err;
});

/plugins/socketIO/index.js

exports.register = function(server, options, next) {
    var io = require('socket.io').listen(server.select('chat').listener,{log:false});
    io.sockets.on('connection', function (socket) {
        socket.on('someAction', function(name, cb) {
           ...
        });
        ...     
   });
}
3
votes

Answer: Load the Client Script from CDN

To answer your specific question: we decided to load the socket.io.js script from the CDN (e.g: http://cdnjs.com/libraries/socket.io ) to make our app load faster. see: index.html#L23

Working Offline ...? (Or Prefer Not to use CDN?)

If loading the client script form CDN is not an option because you are on dial-up or working offline, then use inert and expose the file to your app. e.g:

var Hapi = require('hapi');
var server = new Hapi.Server();

server.connection({
    host: '0.0.0.0',
    port: Number(process.env.PORT || 3000)
});
// uses https://github.com/hapijs/inert to serve static files
server.register(require('inert'), function () {

    server.route([
      { method: 'GET', path: '/', handler: { file: "index.html" } },
      { method: 'GET', path: '/socket.io.js', handler: { file: './node_modules/socket.io-client/socket.io.js' }
    ]);

    server.start(function () {
      console.log('Visit: http://127.0.0.1:'+server.info.port);
    });

});
module.exports = server;

The client file is located in: your_project/node_modules/socket.io-client/socket.io.js

Up-to-Date Solution/Example with End-to-End Tests

If you are still looking for an example of how to use Socket.io in a Hapi.js app we created a complete one (with documentation/comments & end-to-end tests).

see: https://github.com/dwyl/hapi-socketio-redis-chat-example

Build Status Test Coverage by codecov.io Code Climate Dependency Status devDependency Status Its up-to-date with the latest versions of Hapi & Socket.io and uses Redis Pub-Sub to persist and distribute chat messages.

0
votes

You can try to copy the socket.io.js file out from the node.js directory to a well-known directory.

0
votes

I would first confirm that you don't have any firewall issues interfering with the serving of the request.

If a firewall isn't responsible for blocking the request make sure that the src for the javascript file is pointing to the same server and port number, as indicated on the Hapi.createServer line, that you have configured.

If the request reaches the server it will output a debug line in the terminal indicating that it served the file.