Control humidity with Node.js on Raspberry Pi

The End Game

I won’t claim this to be an IoT (Internet of Things) article just because you are going to read about Raspberry Pi. But what I will certainly call it is an Internet Automation project that solves one small problem without me needing to take any action.

Throughout this article I am going to provide a lot of references to external resources that I found useful which will enable us to quickly get to the node.js and JavaScript part of the project.

The Problem Statement

With negative winter temperatures, we want to use heaters to maintain a cozy warm temperature in our homes / offices. However, closed and artificially heated spaces impact humidity levels. We use Humidifiers to the resolve! In the context of this article, I am referring to the portable humidifiers that are connected to an electric outlet.

My goal was to automatically turn the humidifier ON or OFF based on the humidity or temperature levels of the room.

How to even achieve this?

Hardware:

This can be simply achieved if we could automatically control the electric outlet (or the switch) the humidifier would be connected to. So, we need an outlet that can controlled preferably via the internet. For that purpose I used one such internet enabled switch called Wemo Switch from Belkin.

(Please Note: Most portable humidifiers also come with an automated switch or a timer, but the idea is to DIY. So please keep that context as you read this article further)

IFTTT provides a platform called Maker that allows (obviously you will need to signup to their service):

  1. Connecting Wemo Switch to them
  2. Controlling the Wemo Switch state using the Maker API (created specifically for your account and devices)

We obviously need sensors that will be connected to Raspberry Pi. Instead of getting individual sensors and connecting them to the Raspberry Pi, I strongly recommend using Raspberry Pi SenseHAT which is a “hat” on top of Raspberry Pi and contains a lots of sensors already installed. They also provide a rich Python library to get the sensor readings.

Finally, we need Raspberry Pi to be connected to internet also. This is simply achieved by any WiFi dongle that plugs into a Raspberry Pi’s USB port. Of course, WiFi needs to be configured on the Raspberry Pi. (Hint: Use Linux commands or IDE).

Software:

Since Raspberry Pi can run an operating system, such as Linux and Windows, we can easily  install Node.js on it. Thus, node.js provides us with the core backbone for getting readings from the sensors and calling API’s to control the state (ON or OFF) of the Wemo Switch via IFTTT Maker.

As mentioned earlier,  we will also be relying on a lot of python scripts provided by SenseHAT. We will not be covering the python scripts in this article because they are already available on the SenseHAT API reference. We will however be covering how to invoke these python scripts from the node.js application.

Node.js App

The app performs three-stage functions:

  1. Invoke the python scripts that read the sensor data (in this case temperature, but it could also be based on humidity) at frequent intervals
  2. Assess the reading against condition that would lead to whether Wemo Switch needs to be turned ON or OFF
  3. Actually call the IFTTT Maker API discussed earlier to actually turn the connected Wemo Switch ON or OFF

Let’s look at the code for each of these stages below:

Stage 1: Get sensor readings

Node.js provides a module called child_process that provides a method called exec to execute commands from the operating system. This stage relies on this module to invoke the python script. Remember, because we want to invoke the python script at a regular frequency, we wrap this around the setInterval function of JavaScript.

setInterval(function(){
   require('child_process').exec(command, function(error, stdout, stderr) {
      if (error == null) {
          var data = stdout.replace("\n","");
          // ... Call Stage 2
      }
      else {
        console.log("Error occured. " + error);
        }
    }); child_process.exec
}, 60000); // frequency = 60 seconds

Stage 2: Assess Condition

This would be a simple comparison of the reading obtained from Stage 1. However, this is also where you can get all fancy with advanced features like storing the data in database, store last few readings, determine if reading is consistently increasing or decreasing over last few readings, etc. For the sake of this article, we are going to assume the condition is going to be evaluated based on the latest sensor reading.

// assumption: We are looking for Temperature in Stage 1
var YOUR_API_KEY = "?????"; // obtain this from IFTTT
var wemoState = "off"; // or as defined in IFTTT Maker
if(data > 35) { // deg. Celsius is what SenseHat APIs returns
    wemoState = "on";
}
// ... Call Stage 3

Stage 3: Call IFTTT Maker API

As mentioned earlier, we have not covered how to create an IFTTT Maker API that would control the state of an existing device that is registered with IFTTT or yet call another API. You can refer to the maker reference or this blog.

Having said that, now to actually call the API from Node.js, we will use the https module from node.js which provides a request method.

var makerAPI_host = "maker.ifttt.com";
var makerAPI_path = "/trigger/"+wemoState+"/with/key/"+YOUR_API_KEY;
var https = require('https');
 var optionsget = {
 method : "GET",
 host : makerAPI_host, 
 port : 80,
 path : makerAPI_path
 };
var reqGet = https.request(optionsget, function(resp) {
 var str = "";
 resp.setEncoding('utf8');
 resp.on('data', function(d) { // data chunk
 str += d;
 });
 resp.on('end', function() { // all data sent
 console.log(str); // We are Done!
 }); 
});
reqGet.on('error', function(e) {
 error = {
 message : "Error occured",
 error : e
 };
 console.log(error);
});
reqGet.end();

alternatively, can also use the same child_process.exec() method from Stage 2 as below

var callAPI = "curl -X GET https://maker.ifttt.com/trigger/"+wemoState+"/with/key/"+YOUR_API_KEY;    
require('child_process').exec(callAPI, function(error, stdout, stderr) {
   if (error == null) {
      console.log(stdout); // We are Done!
   }
  else {
     console.log("Error occured. " + error);
   }
}); child_process.exec

 

Further Scope

To summarize, while the scope of this article was to demonstrate use of Node.js on Raspberry Pi using various node.js modules, the DIY project also leaves scope for further expansion. One re-use I envision is utilizing the same apparatus to control any other internet-connected  device, such as Nest Thermostat, etc. to create many custom and fancy Internet Automation DIY projects.

Please feel free to comment, share your experience, provide feedback or call out if anything obvious was missed or if any additional perspective needs to be covered.

 

Advertisements

2 thoughts on “Control humidity with Node.js on Raspberry Pi

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