Deploying a NodeJS server with SocketIO to Docker using Azure IoT Edge

The current Azure IoT Edge public preview uses Docker to deploy logic from the cloud into local gateways. It’s currently featuring:

  • C# modules written in .Net standard
  • Python modules
  • Azure Function built on your machine
  • Azure Stream Analytics jobs built and deployed in the cloud
  • Azure Machine Learning

We can expect Microsoft will support other types of modules soon as they have proven with other recent projects. An Azure Cognitive Services module is a good example, it’s put in every IoT Edge presentation.

The IoT Edge portal makes it possible to deploy modules which are available in private or public image repositories.

Could it be possible to build and deploy images to the gateway which are not specifically designed for IoT Edge?

It turns out, it is possible.

Let’s deploy a NodeJS server which serves SocketIO.

This is the last part of a series of blogs:

  1. Deploying a NodeJS server with SocketIO to Docker using Azure IoT Edge
  2. Show telemetry in NodeJS using SocketIO and HighCharts
  3. Visualizing Azure IoT Edge using local dashboard

Creating a Dockerized NodeJS SocketIO server

The NodeJS service is fairly simple to create. Just follow the Chat tutorial and you have a brand new Node JS server which can be reached at port 3000.

For convenience, I switched over to port 80.

After that, I dockerized the NodeJS server using this tutorial.

This resulted in this package.json:

{
  "name": "iotedgelocaldashboard",
  "version": "1.0.1",
  "description": "Local Dashboard for IoT Edge",
  "author": "@svelde",
  "main": "index.js",
  "scripts": {
    "start": "node index.js"
  },
  "license": "ISC",
  "dependencies": {
    "express": "^4.15.2",
    "socket.io": "^2.1.0"
  }
}

After building and pushing the container was available in an Image repository.

Exposing the port

By default, internal ports in a Docker Module are not available from the outside.

So if we would try to deploy the image to our gateway directly, we would have a SocketIO server unreachable for the rest of the world.

Luckily, we can configure the Module to give it a port mapping:

{
 "ExposedPorts": {
   "80/tcp": {}
 },
 "HostConfig": {
   "PortBindings": {
     "80/tcp": [
       {
         "HostPort": "80"
       }
     ]
   }
 }
}

This looks like this:

Note: We can skip Module Twins and specific Routing for this module. It’s deployed by the IoT Edge deployment mechanism but not interacting with the other IoT Edge modules!

So in the end, I have a NodeJS SocketIO Server running. And I can reach it with any browser on my machine. Nice.

Chrome:

Firefox:

But what about programming our own SocketIO Client?

C# .Net Core SocketIO client

The next step was trying to build a client in Visual Studio 2017.

I have built a simple SocketIO client using the NuGet package “SocketIoClientDotNet”.

This results in the following code:

using Quobject.EngineIoClientDotNet.ComponentEmitter;
using Quobject.SocketIoClientDotNet.Client;
using System;

internal class Program
{
  private static void Main(string[] args)
  {
    // https://github.com/Quobject/SocketIoClientDotNet

    Emitter socket;

    socket = IO.Socket("http://localhost:80");

    socket.On(Socket.EVENT_MESSAGE, () =>
    {
      Console.WriteLine(Socket.EVENT_MESSAGE.ToString());
    });

    socket.On("chat message", (data) =>
    {
      Console.WriteLine(data);
    });

    Console.WriteLine("Press a key to exit");
    Console.ReadLine();
  }
}

And if we run this, we get the same output:

So this looks very promising.

What is going happening on the gateway?

Let’s look at Docker on the gateway. This is what we see with “docker ps”:

We see how the module is started and we see how the port is made available.

The last thing to check is the log of the new module. Just type in “docker logs -f ldb”:

Here we can see how the module is started, how three clients are connected and two of them are sending messages.

Conclusion

This is our solution:

We are pushing the usage limit of IoT Edge here 🙂

IoT Edge is not just designed as a plain distribution platform for Docker Modules. If you only use it only for this feature, you are missing out the real power of Azure IoT Edge.

But this gives us a good insight into what Docker is capable of how flexible the IoT Edge solution is.

And I hope Microsoft will support NodeJS by default in IoT Edge. And by support, I mean supporting the routing and the Module Twin. This is a programming/deployment platform for many (IoT) users, I have shown the deployment is working, Microsoft only needs to make libraries available to interact with (standard?) inputs and (standard?) outputs and Module Twin.

Come back shortly, for the second part of this story on how we can make use of NodeJS is a more meaningful way together with IoT Edge.

2 gedachten over “Deploying a NodeJS server with SocketIO to Docker using Azure IoT Edge

Reacties zijn gesloten.