A Websocket Implementation

Websockets are an advanced technology that enable a interactive two-way communication between a client and a server. This means that the client can remain upto date with the server without the need for ajax polling. For more information of websockets read my Introductions To Websockets post.

This post will mainly be about how to implement a websocket client and server using the SOCKET.IO  library.

I will be using a node.js server and a jquery client for this example. However, any client and any server could be used.

The usecase is this. When one user selects a specific color that change should be shown to all the other users connected. If the user selects red, then all users should show red.

The server

I pasted my package.json file below, that way all you have to do is copy the dependencies and get started.

The main libraries needed are socket.io and express, however express is not strictly required.

{
  "name": "socker-server",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "start": "nodemon index.js"
  },
  "author": "Shayne Weerakoon",
  "license": "MIT",
  "dependencies": {
    "express": "^4.14.0",
    "socket.io": "^1.7.2"
  }
}

Creating a websocket server

As I mentioned before, express is not needed, however, having it leaves the option of supporting both REST and websocket implementations on the same server.

var express = require('express');
var app = express();
var server = require('http').createServer(app);
var io = require('socket.io')(server);
var port = process.env.PORT || 3000;
server.listen(port, function() {
    console.log('Server listening at port %d', port);
});

And there you have it. An up and running websocket server.

Now this server won’t do anything. You could connect to it, but that’s it. Add these few lines to give it an endpoint.

//When there is a new client connecting the 'connection' event is fired
//This event has one parameter, the websocket
io.on('connection', function(socket) {
    //Once the intial connection occurs, we
    //can then listen for an event on this
    //specific socket.
    socket.on('change', function(data) {
        //When this particular client pushes a change event
        //the function will be called with the data as a
        //parameter.
        //Logging the data
        console.log('change ', data);
        //this will then emit the 'changed' event
        //to ALL sockets connectd to the server.
        io.sockets.emit('changed', data);
    });
});

The Client

The client requires the socket.io-client package.

Here is the html with buttons for the user to selct a color, a text field to display the color and the required libraries imported.

<!DOCTYPE doctype html>
<html lang="en">
    <head>
        <meta charset="utf-8">
            <title>Websocket Client Example</title>
            <link href="css/index.css" rel="stylesheet"></link>
        </meta>
    </head>

    <body>
        <br><br><br>
        <center>
            <button id="redButton" type="button">Red</button>
            <p id="redStatus"></p>
            <br>
            <button id="greenButton" type="button">Green</button>
            <p id="redStatus"></p>
            <br>
            <button id="blueButton" type="button">Blue</button>
            <p id="redStatus"></p>
            <br>
            <button id="orangeButton" type="button">Orange</button>
            <p id="redStatus"></p>
            <br>
            <button id="yellowButton" type="button">Yellow</button>
            <br><br><br>
            <h3 id="currentColor"></h3>
        </center>
        <script src="lib/jquery/dist/jquery.min.js">
        </script>
        <script src="lib/socket.io-client/dist/socket.io.js">
        </script>
        <script src="js/sample.js">
        </script>
    </body>

</html>

The UI is extremely basic but for the purposes of this tutorial, the job gets done.

The javascript is as follows:

$(function() {
    //Connect to the socket server we started earlier
    var socket = io.connect('http://localhost:3000');
    //listen for any button clicks by the user
    //if a button is clicked call changeCommand function
    //and pass color as parameter.
    $('#redButton').click(function() {
        changeCommand('red')
    })
    $('#greenButton').click(function() {
        changeCommand('green')
    })
    $('#blueButton').click(function() {
        changeCommand('blue')
    })
    $('#yellowButton').click(function() {
        changeCommand('yellow')
    })
    $('#orangeButton').click(function() {
        changeCommand('orange')
    })
    //Function to be performed when a button is clicked,
    //accepts the color as a parameter.
    function changeCommand(color) {
        socket.emit('change', color);
    }
    //the socket will listen for the changed event to be
    //emmited by the server
    //once emitedd will perform the specified function
    socket.on('changed', function(data) {
        //data is the parameter passed by the server
        ////changing color to the passed data
        $('#currentColor').text(data);
    })
});

Once again, very bare bones but it gets the job done.

The Results

The Server on start up:server1

The server after 2 clients connected:

server2

The 2 clients before any changes:

client3.PNG

The server after some changes were made on both sides:

server3

The clients after the changes were made:

client2

Conclusion

As you can see, websockets provide an easy way to provide the user with real time date, without the need to have complex long-polling processes which pose a heavy load on latency and bandwidth. Websockets are far form perfect, and they are definitely far away from being a complete API solution, however for simple usecases like this, websockets will definitely do the job.

 

 

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s