IoT in home automation (Internet of things for home automation)

In this project, I will explain to you how you can use IoT in home automation. I have decided to make a home automation system. Using this automation system, you can control the appliances in your home using a web interface from anywhere in this world. This system will show us the current status of appliances (switches) in real-time on a web interface. Even if you switch off/on your appliance using a manual switch, the web interface will update itself without refreshing. This gives you the ability to monitor your appliances in real-time. In this way, we can monitor as well as control our home appliances from anywhere in the world. I will not use blynk or MQTT server, rather I will create my own.

Components of my IoT home automation system

As said before, you can control the appliances using manual switches also. If you manually press the switches then also the change will be reflected in the web interface in almost no time. To build the web interface, we have used HTML, CSS, Javascript, and PHP language. After building the interface on the local computer I have then hosted all files on a cloud server.

If you don’t have the server then let me tell you that a lot of companies are out there who provide free hosting nowadays. I will suggest you create an account on 000webhost and use the free hosting to test your websites.

The web interface fetches the data (status of the switches) from the database and displays that. If you change the status of any appliance from the interface then the web interface will update the database.

To get the status of home appliances from the database and control them we have used an ESP8266 NodeMCU (ESP8266) Wi-Fi board. This Wi-Fi module also fetches the data from the same database as the web interface and turns On/Off appliances accordingly. If we control the appliances using manual switches then the NodeMCU will update the database. The functionality of NodeMCU is the same as the web interface but the difference here is that it drives the actual appliances also.

Requirements

Hardware

  • NodeMCU Wi-Fi module
  • Relay
  • Transistor (to drive the relay)
  • 10kΩ Resistors (8-10 pieces)

Software

  • Cloud hosting (server)
  • HTML (hypertext markup language)
  • CSS (cascading stylesheet)
  • Javascript
  • PHP

The web interface of my IoT home automation system

Any website has two ends. The first one is the front-end and the second is the backend. The front end is the part of any website where a user interacts and in the backend of any website, the server runs scripts (algorithms) that a programmer writes (such as connecting, fetching data, or updating data to a database).

To build the home automation system you have to first build the front end of the website. Here you will design what our web interface will look like. I have decided to keep our design simple and let take the project in working condition first. Then you can add more designs to it and make it more attractive and interactive. To control and monitor the home we have used the checkbox buttons and labeled them according to appliances in our home. Our next step will be to connect our site to the database.

Web interface of IoT home automation system

I will attach the zip file of my code after the successful operation of the system.

Connect to database

My automation web interface as well as hardware part (NodeMCU) both needs to connect to a storage device from where it can access or modify data to properly control the appliances. If you don’t connect to a database all appliances may turn off as we refresh the page due to data loss. So I need a database to store the previous status of all appliances and use it as a reference after refreshing the page.

To properly work, our system needs to connect to the database and fetch or update data from the database. A database is a data storage system where data is stored in proper formatting. So that anyone can access or modify the data easily. There are a lot of database management systems (DBMS) available nowadays like MongoDB, Oracle, MySQL, etc. I will use MySQL to manage the database because PHP supports it better.

I have made the connection to the database using SQL query with the help of PHP and fetched the data. We have then used that data to check or uncheck the checkbox according to the data using the if condition. Here are the screenshots.

Web interface
The web interface of the automation system
Database of my IoT home automation system
This is the Screenshot of the database (PhpMyAdmin).

You can see that the checkboxes are checked according to the data in the database. If you change the database using PhpMyAdmin or requesting the URL then also the checkboxes will change their status accordingly. Similarly, if you change the status of any checkbox then the database will also change the data respectively. You can extend the web interface and database as your home needs by adding more pages to the web interface and more rows in the database.

Update database from the web interface

Now I have to update that database when we click on any checkbox and store the value in the right column of the database. For that, I have created a separate PHP script file. When we make an HTTP request to that file with the value parameter then the PHP script will update the
database with that value. If you don’t know about HTTP requests then you can read my previous article by clicking here.

In short, making an HTTP request is simply browsing the URL (link) of the PHP file with the values parameters. Here is an example.

localhost/IoTDemo/dbupdate.php?appliance=Light&val=0

Here I am turning off the light using that URL. I have created a file called ‘dbupdate.php’ and created two variables that will store the parameters coming from the URL and then using those I have updated the database. This script also includes the script which has the method to connect to the database. Then I requested that URL to check whether it is working or not. In the URL we have passed the Light in the appliance variable and 0(off) as the val variable. This worked and database updates. Here is the interface screenshot after updating the database.

I have used javascript to track the clicks on every checkbox and make the HTTP request from the web interface.

Update database on manual switch

As said earlier, to update the database I have to request a PHP file on the server. That will run a script and update the database. So in the web interface, I have used javascript to send an HTTP request with the appliance ID and value whenever a checkbox is checked or unchecked.

In the hardware, I have programmed the NodeMCU to make the HTTP request to that ‘dbupdate.php’ script. First, I have detected any manual switch change in NodeMCU as we have done with javascript. Then we requested the same PHP script on the server with the switch ID and value. This will update the database.

As you know when you change the database even by requesting the link then also the web interface will update itself automatically. Because the web interface is continuously checking the database. This way the web interface will also update itself automatically on the manual switch.

Fetch data from the database to update the interface and control the appliance

You know that when we push switches manually then also it updates the database. So, to update the web interface in real-time, you have to check the database frequently. I have done this by javaScript. Using javascript I have first fetched the data from the database after every 1 second in the background. For that, I have used the setInterval function of the javascript. Then we have used that data to update the user interface. This way you will get real-time monitoring without refreshing the page.

To fetch the data from the database, I have created a PHP script called “db_fetch.php”. To fetch the data you just have to make the HTTP request to this URL.

localhost/IoTDemo/db_fetch.php

This script just fetches the data from the database and arranges them to be a binary number. The MSB of that binary number is the “Light” status and the LSB is the “Socket” status. Then it converts that binary number into the equivalent decimal number and sends it. In the user interface, I have then checked the status of every bit and checked/unchecked the checkboxes respectively.

I have done the same thing on the NodeMCU. I have fetched the data from the database by requesting the same PHP script after every 1 second. Then I checked the status of every bit in the NodeMCU and controlled the electrical appliances.

NodeMCU circuit diagram

Programming the NodeMCU (ESP8266)

To complete my IoT-based home automation system, I have to program the NodeMCU to read the button status, update the database and fetch the data from the database. To better understand the function of hardware, let’s have a look at the flowchart of my NoduMCU program.

Now you can take an overview and understand better the functionality of the NodeMCU for my IoT-based home automation system. Now here is the NodeMCu code which I have written in the Arduino IDE.

#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClient.h>

const char* ssid = "YOUR_SSID";
const char* password = "YOUR_PASSWORD";
String Link1 = "//electronics-fun.com/dbupdate.php";
String Link2 = "//electronics-fun.com/db_fetch.php";

uint8_t prevStatus = 0;             //To store previous switches status in binary bits
uint8_t newStatus = 0;              //To store current switches status

//Pins that connects to switches
uint8_t Light_switch = 16;
uint8_t Fan_switch = 5;
uint8_t Refrigerator_switch = 4;
uint8_t Socket_switch = 0;

//pins that connects to appliance
uint8_t Light = 14;
uint8_t Fan = 12;
uint8_t Refrigerator = 13;
uint8_t Socket = 15;

WiFiClient client;
HTTPClient http;
      
void setup() {
  //defining switches pins as input
  pinMode(Light_switch, INPUT);
  pinMode(Fan_switch, INPUT);
  pinMode(Refrigerator_switch, INPUT);
  pinMode(Socket_switch, INPUT);

  //Defines applicances pins as output
  pinMode(Light, OUTPUT);
  pinMode(Fan, OUTPUT);
  pinMode(Refrigerator, OUTPUT);
  pinMode(Socket, OUTPUT);
    
  ConnectToWifi();
}

void loop() {
    //reading switches status and shifting the value of equivalent switches bit (MSB is Light)
    newStatus = newStatus<<0|digitalRead(Light_switch);
    newStatus = newStatus<<1|digitalRead(Fan_switch);
    newStatus = newStatus<<2|digitalRead(Refrigerator_switch);
    newStatus = newStatus<<3|digitalRead(Socket_switch);

    //Performing XOR operation to check flipped (changed) bit in current status and previous status
    uint8_t changes = prevStatus^newStatus;

    //updating the status of changed bit (switches) to the database
    if((changes>>0)&1)UpdateServer("socket", String((newStatus>>0)&1));
    if((changes>>1)&1)UpdateServer("refrigerator", String((newStatus>>1)&1));
    if((changes>>2)&1)UpdateServer("fan", String((newStatus>>2)&1));
    if((changes>>3)&1)UpdateServer("light", String((newStatus>>3)&1));

    //fetch data from database
    uint8_t database = GetData();
    prevStatus = database;              //store current database value to use as previous data in next cycle

    //Turning appliances on/off according to fetched data
    ((database>>0)&1)?digitalWrite(Socket,HIGH):digitalWrite(Socket,LOW);
    ((database>>1)&1)?digitalWrite(Refrigerator,HIGH):digitalWrite(Refrigerator,LOW);
    ((database>>2)&1)?digitalWrite(Fan,HIGH):digitalWrite(Fan,LOW);
    ((database>>3)&1)?digitalWrite(Light,HIGH):digitalWrite(Light,LOW);

    if(WiFi.status()!= WL_CONNECTED){
      ConnectToWifi();
    }
    delay(1000);
}

//Method to coonect to wifi
void ConnectToWifi(){
   WiFi.begin(ssid, password);
  while(WiFi.status() != WL_CONNECTED) {
    delay(500);
  } 
}

//Method to update database
void UpdateServer(String Appliance, String value){
      Link1 = Link1+"?appliance="+Appliance+"&val="+value;
      http.begin(client, Link1);          
      http.GET();
      http.end();
}

//Method to fetch database
uint8_t GetData(){
      http.begin(client, Link2);          
      int httpResponseCode = http.GET();
      if(httpResponseCode==200){
        return http.getString().toInt();
      }
      http.end();
}

Code explanation

In code, I first defined the SSID and password of my router. Then I declared two variables of the data type string and stored the links to update the database and fetch the database. I have also declared two variables to store the previous switches’ status and current switches’ status. Later I used those data to detect the switch status change. That data stores the switch status in binary format. For example, if the data is 0110 then it is representing that light is off, the fan is on, the fridge is also on, and the socket is off.

If you have previous status and current status in the binary format you can detect changes in bits by just performing an XOR operation between those numbers. For example, let’s say you have 1011 as the previous status and 1001 as the current status. If you perform an XOR operation between them you will get 0010.

So as you can see that here 1 in the resultant binary number represents the bit position of flipped in the previous and current status. So, by detecting the set bits in the resultant binary number you can find the flipped bit’s position and performing AND operation from 1 on that bit of the current status number, you can get the value of the flipped bit.

Back to the code. I have defined the pin mapping of switches and appliances. Then I have declared the switch pins as input and appliance pins as output.

In the loop function, I have scanned every switch pin and stored the status of every switch on its equivalent bit in the newStatus variable. Then I checked the changes in new data according to the algorithm I just discussed and updated the database.

Then I fetched the data from the database and turned on/off electrical appliances according to bits of database data.

Here is the complete code for creating user interface and backends scripts

Leave a Comment

Your email address will not be published. Required fields are marked *