Displaying MQTT messages in a browser in real time
I have recently been investigating how to display MQTT messages in a web browser in real time. The MQTT server I use is Mosquitto as it is light weight and can be run on low power (ARM) devices, ideal if you want to use a Raspberry Pi as a gateway for sensors around your house.
Enter RabbitMQ, a popular and widely deployed AMQP broker which has a MQTT plugin and a Web Stomp plugin that allows a web browser to subscribe to messages using the Stomp protocol over a websocket.
MQTT brokers have a neat feature called bridging which allows one broker to publish and receive messages from another broker without you having to write any code.
So, its time to put all this together. As I mentioned, Mosquitto is ideal for running on low power devices and RabbitMQ is commercially supported and can be scaled to deal with millions of messages a second. After installing Mosquitto on my ARM device, I installed RabbitMQ on an EC2 instance, I then set up a bridge between the two, with Mosquitto sending every message it receives to RabbitMQ. Finally I created a web page that is able to display these messages to a user in real time.
Setting up RabbitMQ
See http://www.rabbitmq.com/download.html for instructions on how to install RabbitMQ. If you are deploying on EC2 or similar you will need to make sure the following ports are open:
|5672||Used to send/receive AMQP messages|
|1883||Used to send/receive MQTT messages|
|15674||Used to send/receive STOMP messages|
|15672||Optional Used by the web management plug-in|
Once installed we need to enable the MQTT and Web Stomp plugins. We do this by running
$ rabbitmq-plugins enable rabbitmq_mqtt
$ rabbitmq-plugins enable rabbitmq_web_stomp
$ rabbitmq-plugins enable rabbitmq_management # optional
Once you restart RabbitMQ server the plugins will be enabled.
Setting up Mosquitto
Next we need to install Mosquitto on our Raspberry Pi. Make sure you get the latest version of Mosquitto, for instructions on how to get the latest release for your OS/Architecture see http://mosquitto.org/download/. The Debian repository contains ARM versions that will work with the Raspberry PI. You may have to add the package version to the usual apt-get command to install the latest release, apt-cache show mosquitto will list all the versions available to you.
$ apt-get install mosquitto=1.2.2-0mosquitto1
We then need to add the bridge to our config file. You can read the full details of how to create bridges in the Mosquitto.conf man page but for now I will just describe what we need for our setup. Edit /etc/mosquitto/mosquitto.conf adding the following to the Bridges section:
So, firstly we give our connection a name (every connection in a config file must have a unique name). Secondly, we tell Mosquitto the address of the broker we want it to bridge with. Thirdly, we describe how we want topics to be shared among the two brokers. The topic keyword is described as:
topic pattern [[[ out | in | both ] qos-level] local-prefix remote-prefix]
So we have set our pattern to ‘’#’’ which in MQTT means everything (think posix ‘’*’’), we have specified we want communication to be two way, ‘‘both’’, our QOS level is set to 0, and we are mapping everything sent to the local ‘‘sensor/’’ topic, to the remote ‘‘sensor/jons-house’’ topic.
Now, lets test our set up so far using the Mosquitto command line tools. In one terminal window on the Raspberry Pi we will subscribe to the topic on the RabbitMQ host (you can do this from any machine and you should see the same result):
$ mosquitto_sub -h <rabbitmq-url> -t topic/sensor/jons-house/#
'’topic’’ is the name of the exchange used by default on RabbitMQ.
And in a second window we will publish messages to the local Mosquitto broker (this needs to be run on the Pi):
$ mosquitto_pub -h sensor/kitchen/temperature -m “22.3C”
If everything worked correctly you should see “22.3C” printed in the subscriber terminal window. The only problem is that the ‘‘kitchen/temperature’’ part of the topic is lost due to our bridge, if this is important to you, change the topic line to something like:
topic kitchen/temperature/ both 0 sensor/ sensor/jons-house/
Now everything sent to the local ‘‘topic/kitchen/temperature’’ topic will appear on RabbitMQ as ‘‘sensor/jons-house/kitchen/temperature’’. This allows more information to be passed on, but also means you need to explicitly create a topic line for every topic you wish to bridge. A middle ground may be to publish json messages rather than just the temperature to the ‘‘sensor’’ topic but that too has pros and cons. It is up to you to decide what works best for your installation.
Creating our web application
Finally we need to create a simple web application to start displaying the readings in real time. First, we need to create a simple HTML page:
You can download stomp.js from the Stomp Websocket github page.
python -m SimpleHTTPServer
If you now open http://localhost:8000 in your browser you should be able to see any message you send using the mosquitto_pub tool.