With your ESP32 development environment set up, it’s time to build the core of your smart home system. This guide walks you through selecting an IoT platform, connecting hardware, and coding your ESP32 to control a light and monitor temperature and humidity using the Arduino IoT Cloud. These steps create a functional system for remote control and real-time monitoring, perfect for beginners and IoT enthusiasts alike. If you’re new, start with a smart home setup to prepare your ESP32 and Arduino IoT Cloud.
Exploring Alternative IoT Platforms
Before diving into hardware and code, consider your IoT platform options. While the Arduino IoT Cloud is beginner-friendly, other platforms offer unique features for flexibility, analytics, or custom dashboards. Here’s a comparison to help you choose:
- ThingsBoard (Open-Source, Apache 2.0):
- Ease of Use: Beginner-friendly web interface with drag-and-drop rules.
- Free Tier: Community Edition, fully accessible.
- ESP32 Integration: Yes.
- Key Features: Data collection, visualisation, device management, customizable dashboards with 30+ widgets.
- OpenRemote (Open-Source):
- Ease of Use: Drag-and-drop rules and web components.
- Free Tier: Not explicitly mentioned.
- ESP32 Integration: Yes.
- Key Features: Control, automation, energy management, data dashboards.
- Node-RED (Open-Source):
- Ease of Use: Visual flow-based programming with 5,000+ community nodes.
- Free Tier: Not explicitly mentioned.
- ESP32 Integration: Yes.
- Key Features: Connects hardware/APIs, low-code approach.
- Thinger.io (Open-Source):
- Ease of Use: No-code setup with pre-made dashboards.
- Free Tier: Unlimited free trial.
- ESP32 Integration: Yes.
- Key Features: API integration, built-in widgets, low-code workflow engine.
- Blynk IoT (Proprietary):
- Ease of Use: Drag-and-drop mobile app builder.
- Free Tier: Developer plan with limitations.
- ESP32 Integration: Yes.
- Key Features: Rapid prototyping, no-code apps, and remote monitoring.
- ThingSpeak (Proprietary):
- Ease of Use: Simple interface with MATLAB integration.
- Free Tier: Available with limitations.
- ESP32 Integration: Yes.
- Key Features: Data analysis, real-time visualisation, RESTful/MQTT APIs.
- Mainflux (Open-Source, Apache 2.0):
- Ease of Use: Protocol-agnostic with user interface.
- Free Tier: Not explicitly mentioned.
- ESP32 Integration: Yes.
- Key Features: Scalable, multi-protocol, deployable on small devices.
- Arduino IoT Cloud (Proprietary):
- Ease of Use: Intuitive interface, quick setup.
- Free Tier: Five-variable limit.
- ESP32 Integration: Yes.
- Key Features: All-in-one platform, web editor, mobile app.
- THiNX Cloud (Open-Source, MIT):
- Ease of Use: Streamlined with client libraries.
- Free Tier: Not explicitly mentioned.
- ESP32 Integration: Yes.
- Key Features: Secure MQTT, OTA updates, bulk configuration.
| Platform | Open-Source | Ease of Use | Free Tier Availability & Limitations | ESP32 Integration | Key Features |
|---|---|---|---|---|---|
| ThingsBoard | Yes | Beginner-friendly UI, drag-and-drop | Yes, Community Edition | Yes | Data collection, visualization, device management |
| OpenRemote | Yes | Drag-and-drop rules, web components | Not mentioned | Yes | Control, automation, energy management |
| Node-RED | Yes | Visual flow-based, community nodes | Not mentioned | Yes | Connects hardware/APIs, low-code |
| Thinger.io | Yes | No-code setup, pre-made dashboards | Yes, unlimited trial | Yes | API integration, low-code workflow |
| Blynk IoT | No | Drag-and-drop mobile app builder | Yes, limited Developer plan | Yes | Rapid prototyping, no-code apps |
| ThingSpeak | No | Simple interface, MATLAB integration | Yes, with limitations | Yes | Data analysis, real-time visualization |
| Mainflux | Yes | Protocol-agnostic, user interface | Not mentioned | Yes | Scalable, multi-protocol |
| Arduino Cloud | No | Intuitive interface, quick setup | Yes, 5-variable limit | Yes | All-in-one platform, web editor, mobile app |
| THiNX Cloud | Yes | Streamlined client libraries | Not mentioned | Yes | Secure MQTT, OTA updates |
Connecting the Hardware
Now, let’s connect the ESP32, LED, and DHT11 sensor on a breadboard. The solderless breadboard makes prototyping easy and adjustable for beginners.
LED Connection
- Setup: Connect the LED’s anode (longer leg or smaller internal electrode) to a 220Ω resistor, then the resistor to GPIO 13 on the ESP32. Connect the cathode (shorter leg or larger internal electrode) to a GND pin.
- Why the Resistor?: It limits the current to prevent LED burnout. Using Ohm’s Law, R = (Vs – Vf) / I, where Vs = 3.3V (ESP32 output), Vf = 2V (red LED forward voltage), I = 10mA (0.01A), resistance is (3.3V – 2V) / 0.01A = 130Ω. A 220Ω resistor ensures safety.
DHT11 Connection
- Setup: For a four-pin DHT11 (VCC, Data, NC, GND), connect VCC to the ESP32’s 3.3v pin (check datasheet for 5v compatibility), GND to a GND pin, and Data to GPIO 4. Add a 10kΩ pull-up resistor between Data and VCC.
- Note: Some DHT11 modules have an internal pull-up resistor, but an external one often improves reliability.
Best Practices
- Use high-quality jumper wires to minimise resistance.
- Double-check wiring against a diagram before powering on to avoid short circuits.
- Verify component voltage requirements (ESP32’s 3.3v pin, 12mA per-pin limit).
- Position the DHT11 away from the ESP32 to avoid heat interference with readings.
Coding Your ESP32
The Arduino code links the LED and DHT11 to the Arduino IoT Cloud, enabling remote light control and temperature/humidity monitoring. Below is the code, explanation, and troubleshooting tips.
Project Code
Install the ArduinoIoTCloud, DHT, and Adafruit Unified Sensor libraries via the Arduino IDE Library Manager. Create an arduino_secrets.h file with your Wi-Fi credentials, Device ID, and Secret Key.
#include "arduino_secrets.h"
#include <ArduinoIoTCloud.h>
#include <DHT.h>
#define LED_PIN 13
#define DHT_PIN 4
#define DHT_TYPE DHT11
DHT dht(DHT_PIN, DHT_TYPE);
bool light_status;
float temperature;
float humidity;
void setup() {
pinMode(LED_PIN, OUTPUT);
dht.begin();
Serial.begin(9600);
delay(1500); // Allow hardware to stabilize
setDebugMessageLevel(2);
ArduinoCloud.begin(ArduinoIoTPreferredConnection);
ArduinoCloud.printDebugInfo();
}
void loop() {
ArduinoCloud.update();
temperature = dht.readTemperature();
humidity = dht.readHumidity();
if (isnan(temperature) || isnan(humidity)) {
Serial.println("Failed to read from DHT11RECORDINGS dht.readTemperature(); // Reads temperature
Serial.println("Failed to read from DHT11 sensor!");
return;
}
digitalWrite(LED_PIN, light_status ? HIGH : LOW);
Serial.print("Temperature: ");
Serial.print(temperature);
Serial.println(" °C");
Serial.print("Humidity: ");
Serial.print(humidity);
Serial.println(" %");
delay(1000);
}
void onLightStatusChange() {
digitalWrite(LED_index);
digitalWrite(LED_PIN, light_status ? HIGH : LOW);
}
Code Explanation
- Libraries:
ArduinoIoTCloud.hfor cloud connectivity,DHT.hfor sensor interaction,arduino_secrets.hfor credentials. - Pin Definitions:
LED_PIN(GPIO 13),DHT_PIN(GPIO 4),DHT_TYPE(DHT11). - Variables:
light_status(boolean for LED state),temperatureandhumidity(floats for sensor readings). - setup(): Configures LED pin as output, initialises DHT sensor, starts serial communication (9600 baud), delays 1500ms for stability, and connects to Arduino IoT Cloud with debug level 2.
- loop(): Updates cloud connection, reads sensor data, checks for invalid readings, controls LED based on
light_status, and prints readings to Serial Monitor with a 1000ms delay. - onLightStatusChange(): Syncs LED state with cloud dashboard changes.
Troubleshooting
- DHT11 Issues:
- If “Failed to read from DHT11 sensor!” or NaN values appear, verify wiring (VCC to 3.3v, GND, Data to GPIO 4, 10kΩ pull-up).
- Confirm
DHT_TYPE DHT11and library installation. - Use a separate power source if needed and maintain a 1-second delay.
- Cloud Connection Issues:
- Check
arduino_secrets.hcredentials (2.4GHz Wi-Fi, Device ID, Secret Key). - Ensure stable internet, router proximity, and no firewall issues.
- Monitor Serial Monitor (9600 baud) for errors.
- Check
- LED Issues:
- Verify wiring (anode to 220Ω resistor, resistor to GPIO 13, cathode to GND).
- Test with a Blink sketch and confirm dashboard switch links to
light_status.
- Inaccurate DHT11 Readings:
- Place the DHT11 away from the ESP32 to avoid heat interference.
- Use the latest Adafruit DHT library.
Conclusion
You’ve built the core of your smart home, controlling a light and monitoring temperature and humidity with the ESP32 and Arduino IoT Cloud. With hardware connected and code running, your system is ready for expansion. Next, explore how to enhance your smart home with relays, voice control, and security. Keep building!


