Cirkit Designer Logo
Cirkit Designer
Your all-in-one circuit design IDE
Home / 
Project Documentation

ESP8266 NodeMCU with DHT11 Sensor for MQTT-Based Temperature and Humidity Monitoring

Image of ESP8266 NodeMCU with DHT11 Sensor for MQTT-Based Temperature and Humidity Monitoring

Circuit Documentation

Summary

This circuit is designed to measure temperature and humidity using a DHT11 sensor and an ESP8266 NodeMCU microcontroller. The ESP8266 NodeMCU reads the data from the DHT11 sensor and sends this information to a server. The server can display the temperature and humidity on a web page and also send the data to a home automation system using MQTT messages. The circuit is powered through the NodeMCU's 3V3 pin, and the DHT11 sensor is connected to one of the digital pins for data communication.

Component List

DHT11 Temperature and Humidity Sensor

  • Description: A basic, ultra low-cost digital temperature and humidity sensor.
  • Pins:
    • DATA: Digital data pin for sensor output.
    • GND: Ground.
    • VCC: Power supply (3-5V).

ESP8266 NodeMCU

  • Description: A low-cost Wi-Fi microchip with full TCP/IP stack and microcontroller capability.
  • Pins:
    • D0-D8: General purpose I/O pins.
    • RX, TX: UART communication pins.
    • A0: Analog input pin.
    • RSV, SD3, SD2, SD1, CMD, SD0, CLK: SD card interface.
    • EN: Chip enable.
    • RST: Reset pin.
    • 3V3: 3.3V power supply.
    • GND: Ground.
    • VIN: Voltage input for power supply.

Socket

  • Description: A generic socket component, possibly for power supply.
  • Pins:
    • Positive: Positive power supply.
    • Negative: Ground connection.

Wiring Details

DHT11 Sensor

  • DATA connected to ESP8266 NodeMCU D1.
  • GND connected to ESP8266 NodeMCU GND.
  • VCC connected to ESP8266 NodeMCU 3V3.

ESP8266 NodeMCU

  • 3V3 connected to DHT11 VCC.
  • GND connected to DHT11 GND.
  • D1 connected to DHT11 DATA.

Documented Code

ServerTemperature.ino

/*********
 * ServerTemperature.ino
 * Author: Domenico Coriale
 * 
 * This project is used to detect the temperature, humidity, date and specific month.
 * These information are sent to home assistent with MQTT message.
 * It also initializes the sensors in Home assistant via MQTT Discovery.
 * 
 * 
 * Projects used for reference: 
 * Rui Santos - https://randomnerdtutorials.com/esp8266-dht11dht22-temperature-and-humidity-web-server-with-arduino-ide/
 * Werner Rothschopf - https://werner.rothschopf.net/202011_arduino_esp8266_ntp_en.htm
 * Mauro DeBerdis - https://www.maurodeberardis.it/index.php?option=com_jdownloads&Itemid=339&view=viewdownload&catid=154&cid=571
 * 
*********/

// Import required libraries
#include <Arduino.h>
#include <ESP8266WiFi.h>
#include <Hash.h>
#include <ESPAsyncTCP.h>
#include <ESPAsyncWebServer.h>
#include <Adafruit_Sensor.h>
#include <DHT.h>
#include <time.h>
#include <PubSubClient.h>
#include <ArduinoJson.h>

// Network credentials and MQTT configuration are stored in a separate header file
#include <NetworkCredentials.h>

#define DHTPIN 5     // Digital pin connected to the DHT sensor
// Uncomment the type of sensor in use:
#define DHTTYPE    DHT11     // DHT 11

DHT dht(DHTPIN, DHTTYPE);
WiFiClient wificlient;
PubSubClient client(wificlient);

// current temperature & humidity, updated in loop()
float temperature = 0.0;
float humidity = 0.0;
#define MY_NTP_SERVER "pool.ntp.org"
#define MY_TZ "CET-1CEST,M3.5.0/02,M10.5.0/03"  // Timezone per Roma, Italia

String datetime; //data e ora della misura del sensore
String weekDays[7]={"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"};
String months[12]={"January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"};

// Global variables
time_t now;  // Current time in epoch format
tm tm;       // Struct for formatted time

// Create AsyncWebServer object on port 80
AsyncWebServer server(80);

unsigned long previousMillis = 0;    // will store last time DHT was updated

// Updates DHT readings every 10 seconds
const long temperatureAndHumidityInterval = 10000;  

const char index_html[] PROGMEM = R"rawliteral(
<!DOCTYPE HTML><html>
<head>
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.7.2/css/all.css" integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr" crossorigin="anonymous">
  <style>
    html {
     font-family: Arial;
     display: inline-block;
     margin: 0px auto;
     text-align: center;
    }
    h2 { font-size: 3.0rem; }
    p { font-size: 3.0rem; }
    .units { font-size: 1.2rem; }
    .dht-labels{
      font-size: 1.5rem;
      vertical-align:middle;
      padding-bottom: 15px;
    }
  </style>
</head>
<body>
  <h2>ESP8266 DHT Server</h2>
  <p>
    <i class="far fa-clock"></i>
    <span class="dht-labels">D/H</span> 
    <span id="datetime">%DATETIME%</span>
  </p>
  <p>
    <i class="fas fa-thermometer-half" style="color:#059e8a;"></i> 
    <span class="dht-labels">Temperature</span> 
    <span id="temperature">%TEMPERATURE%</span>
    <sup class="units">&deg;C</sup>
  </p>
  <p>
    <i class="fas fa-tint" style="color:#00add6;"></i> 
    <span class="dht-labels">Humidity</span>
    <span id="humidity">%HUMIDITY%</span>
    <sup class="units">%</sup>
  </p>
</body>
<script>
setInterval(function ( ) {
  var xhttp = new XMLHttpRequest();
  xhttp.onreadystatechange = function() {
    if (this.readyState == 4 && this.status == 200) {
      document.getElementById("datetime").innerHTML = this.responseText;
    }
  };
  xhttp.open("GET", "/datetime", true);
  xhttp.send();
}, 10000 ) ;

setInterval(function ( ) {
  var xhttp = new XMLHttpRequest();
  xhttp.onreadystatechange = function() {
    if (this.readyState == 4 and this.status == 200) {
      document.getElementById("temperature").innerHTML = this.responseText;
    }
  };
  xhttp.open("GET", "/temperature", true);
  xhttp.send();
}, 10000 ) ;

setInterval(function ( ) {
  var xhttp = new XMLHttpRequest();
  xhttp.onreadystatechange = function() {
    if (this.readyState == 4 and this.status == 200) {
      document.getElementById("humidity").innerHTML = this.responseText;
    }
  };
  xhttp.open("GET", "/humidity", true);
  xhttp.send();
}, 10000 ) ;
</script>
</html>)rawliteral";

int sensorNumber = 1;
String mqttTopicTempSensor = "crotone/living_room/esp8266_temperatureHumiditySensor_" + String(sensorNumber) + "/";
String stateTopicTempSensor = mqttTopicTempSensor + "state";

// Replaces placeholder with DHT values
String processor(const String& var){
  //Serial.println(var);
  if(var == "TEMPERATURE"){
    return String(temperature);
  } else if(var == "HUMIDITY"){
    return String(humidity);
  } else if(var == "DATETIME"){
    return String(datetime);
  }
  return String();
}

void sendMQTTTemperatureDiscoveryMsg() {
  String discoveryTopic = "homeassistant/sensor/living_room_sensor_" + String(sensorNumber) + "/temperature/config";

  DynamicJsonDocument doc(1024);
  doc["name"] = "Living Room - Sensor:" + String(sensorNumber) + " Temperature";
  doc["unique_id"] = "living_room_sensor_" + String(sensorNumber) + "_temperature";
  doc["stat_t"]   = stateTopicTempSensor;
  doc["unit_of_meas"] = "°C";
  doc["dev_cla"] = "temperature";
  doc["frc_upd"] = true