The IoT, Internet of Things, has arrived.  Sensors are everywhere, collecting more and more data about us and the world around us.  Temperature, Humidity, Fluid Levels, Traffic counts, the status of devices and things like doors and elevators are being collected and distributed all around us.   The question now is "What do we do with all that data?   Of course, analytics is one answer; you can collect traffic counts to see where your customers are congregating, and temperature and humidity sensors can help keep track of building energy use.  In an earlier set of blogs, my colleague, Darren Mallette, does a great job explaining just what the IoT is all about, and how to monitor some of the devices that are used to collect and consolidate that data.

In this series of blogs, I'll discuss how you might collect and use the sensor data itself, not so much for long term analytics; but for "right now" decision making and information.   For example, your IT HelpDesk and CIO might want to know that the temperature in your data center, or satellite office had exceeded some threshold, perhaps due to an air conditioning failure, before your computers started crashing or your employees started complaining or becoming ill.  The sensors and the data are there, all we need to do is collect and act on it.  If you're a Foglight user, you have all the tools at your disposal to do just that.   

In this part I'll walk you through what I did to set up a script agent to monitor the temperature of two freezers we have at home; so we'll never (again) loose a freezer full of food due to a door left open, a plug pulled or a mechanical failure.  You can use these same tools to monitor any other sensors that use MQTT.

MQTT?  Is that a bug? 

In order to be useful a sensor has to communicate.   Some sensors, for example, thermostats, and some newer refrigerators and freezers, communicate using displays located on or near the sensor.  That's great if there's someone around to watch the sensor, and if the sensor can be connected to a reliable power source.  But, what is the sensor's not in the same building or state, or if it there are power constraints.  Running power and data cables everywhere is expensive.   Even WiFi or "wireless ethernet" is "overkill" when all you need is an occasional temperature reading, or if you have a need for a large number of readings.  Dairy farms need to keep track of each cow, imagine each cow with it's own IP address. 

There's an easier way. Most sensors today use some sort of radio or "RF" (Radio Frequency) device to transmit their data; but transmission and reception of a signal only part of the solution.  We have to encode and decode our data onto that signal. That's where, MQTT, or MQ Telemetry Transport, comes it.   According to the MQTT web site:

"MQTT stands for MQ Telemetry Transport. It is a publish/subscribe, extremely simple and lightweight messaging protocol, designed for constrained devices and low-bandwidth, high-latency or unreliable networks. The design principles are to minimize network bandwidth and device resource requirements whilst also attempting to ensure reliability and some degree of assurance of delivery. These principles also turn out to make the protocol ideal of the emerging “machine-to-machine” (M2M) or “Internet of Things” world of connected devices, and for mobile applications where bandwidth and battery power are at a premium."

It's also now an OASIS (Organization for the Advancement of Structured Information Standards) standard, which means it's used by many devices and supported by many different vendors and products.  There are MQTT brokers, clients and servers for many platforms and languages from Arduino to IBM-P series servers and C to Python.  In fact, one popular broker from the Eclipse Project is actually named Mosquitto

Keeping my frozen food frozen

I have two freezers at home, one of which is very old.  While it's still working, I'm concerned that at some point it will stop.   I also have a weather station, which receives data from different sensors over radio link.  It turns out that the same company that makes my weather sensors also has a freezer sensor, that displays the current temperature on a small LCD screen and will send that data to my weather station.  I also have some software, weewx, written in python, that displays that data on a web page.  You can view that web page here.   The problem is that there's no alerting or alarming built into the hardware or software.  But, I'm running Foglight in my lab and already monitoring the Raspberry Pi that hosts the weewx software.  For information on how to monitor Raspberry Pi, or any other Single Board computer, see this blog.

The weewx software has the ability to "publish" the data it collects as MQTT "topics".  So, I can publish the freezer temperature readings and then use Foglight to send an email (which I can read from my SmartPhone) if the freezer temperatures start to rise.  Here's how I did this.

MQTT Software

MQTT uses a "publish and subscribe" model.   "Things" with data to share publish that data as a "topic", then software that wants to access the data can subscribe to that topic.  The publishers and subscribers are "clients" of an MQTT "broker".   In my case, I chose the Mosquitto broker and actually run it in the same Raspberry Pi as the weewx software.  weewx has a built-in publisher; so here I'll concentrate here on the subscription software and getting the data into Foglight.   For the subscriber, I'll use the Eclipse Paho MQTT client.

Choosing an agent

The first choice we have to make is what sort of agent to use.  An SDK agent; built with the Foglight Agent SDK, or a Script Agent.  For this application, at least in the prototype phase, I chose a script agent.    There are two "subtypes" of script agents; type one, which Foglight executes once every collection cycle, and type two, which Foglight executes and leaves running.  To keep things simple, and since my weather station only publishes data every 5 minutes, I chose a type one agent.   At some point, I may decide to enhance to either a type two agent or perhaps even a more generic agent that can be used to subscribe to any MQTT topic, stay tuned.

Coding the agent

For most IoT work, python is my "go to" language; it's reasonably fast, and has a number of extensions that make processing lists and name, value pairs very easy.   Here's the agent code:

  1 #!/usr/bin/python
  3 import paho.mqtt.client as mqtt
  5 import time
  6 import json
  8 def on_connect(client, userdata, flags, rc):
  9     if rc != 0:
 10         print("Connection returned: ", rc)
 11         exit(1)
 13 def on_message(client, userdata, message):
 14     try:
 15         print "START_SAMPLE_PERIOD"
 16         data=dict(json.loads(message.payload))
 17         for key, value in data.items():
 18             if key == "date":
 19                 continue
 20             ps =" = " + key
 21             print ps
 22             ps = "Tempurature= " + value
 23             print ps
 24             print "END_SAMPLE_PERIOD"
 25     except Exception as e:
 26         print("Exception ",e.__class__,"occurred")
 27         exit(2)
 29 def main():
 30     broker_address=""
 31     client = mqtt.Client("P1") #create new instance
 32     client.connect(broker_address) #connect to broker
 33     client.on_connect = on_connect
 34     client.on_message=on_message #attach function to callback
 35     print("TABLE Weather")
 36     client.loop_start() #start the loop
 37     client.subscribe("temps/#")
 38     time.sleep(.1)
 39     print("END_TABLE")
 40     client.loop_stop()
 41     client.disconnect()
 42     exit(0)
 44 if __name__ == '__main__':
 45     main()

Let's start at the high level and look first at main.   The first thing we have to do is set up the broker address and create an mqtt client object (lines 30 and 31).  If I wasn't running all of the systems on a wired network behind a SonicWall firewall,  could also set up a username and password.  The Paho client uses "loop and callback" processing, so we have to define the callback functions we'll use to make sure we have a connection and then actually process the data.   Lines 33 and 34 make those definitions.   Line 36 actually starts the processing loop and then line 37 subscribes to the "temps" topic. The "#" is a "wild card" that picks up all messages in that topic.   I could have selected only one and then written two or three agents; but, it seems easier to process all the data in one agent. At this point the main process goes to sleep to give the loop functions time to get connected and retrieve a message.   On the publisher side, I've set the "retain" flag on my messages, to be sure there's always a message available.

The on_connect function is straightforward, we'll just exit if we can't establish a connection.

The on_message function does all of the work.  Here, I'm making use of the python "dict" type to parse out name, value pairs.  There's a timestamp on message that I'll just ignore and then just loop through the other items in the list.

After a short nap, the main process wakes up, stops the loop and disconnects.   MQTT experts might ask, "Why not just loop forever and process the messages as they show up?".   That would have made this a "type 2" agent.  As I'm just starting to work with MQTT, I wanted to keep things simple.  Look for that change in release 2.

After all that, here's a look at the output:

TABLE Weather
START_SAMPLE_PERIOD = upright_temp
Tempurature= -8.35
END_SAMPLE_PERIOD = outside_temperature
Tempurature= 67.73
END_SAMPLE_PERIOD = chest_temp
Tempurature= -14.12

Register the agent with Foglight

Now we have to register our script agent with Foglight.  We'll use the Administration-Tooling->Script Agent Builder dashboard to make that happen.   Detailed steps can be found in this blog.

Using the data 

Now that we have the data in a Foglight table, we can use it for alarms and also do some graphing.  Since this is a script agent, the data is found under the agent name under Administration->All Agents->(agent name)->Tables, and in our case, the sensor name and metric name (for example, "Weather_chest_temp" and "temperature". 

Here's a rule I created that alarms if either of our freezers gets above thresholds that I defined as Foglight Registry variables.

Note that I used scoping to select just the two freezer sensors.

Here's code for the Warning condition.

Since the thresholds are defined as Registry Variables, It was easy to test all of my notifications.

Wrapping it all up

There are literally thousands of "Things"  that sense and report data about the world around us.  Now that MQTT is an accepted standard, more and more of these will be communicating using MQTT.   In this blog, I've shown an easy way to extract the data from these "Things" and collect it in Foglight, where you can send alerts and alarms, and create dashboards.   Look for improvements and updates to this agent in the future.

Related Content