Quick Start
1
Register your devices
Go to Manage Devices and add a device.
The device_name you enter must exactly match
the name used in your code.
2
Choose your platform
Pick ESP8266, Arduino+ESP8266, or Raspberry Pi Pico W.
Download the matching code file below. Your API key is already filled in.
3
Add your sensors
Write one read function per sensor (Step 1 in the code),
then add one row to the SENSORS[] table (Step 2).
No other changes needed.
4
Set WiFi & server
Fill in WIFI_SSID,
WIFI_PASSWORD, and confirm
SERVER points to the correct URL.
Flash and open Serial Monitor.
Device Code
Your API key is pre-filled in all code blocks below.
For sensor snippets (DHT11, HC-SR04, MQ-2, etc.) see the
Sensor Library tab.
Board: NodeMCU 1.0 (ESP-12E) |
Libraries: ESP8266WiFi, ESP8266HTTPClient, ArduinoJson v6.x |
Baud: 115200
esp8266_monitor.ino
/*
* ════════════════════════════════════════════════════════════════
* ESP8266 — Multi-Sensor Monitor | IoT Platform
* Production-ready • Add unlimited sensors in 2 steps
* ════════════════════════════════════════════════════════════════
*
* HOW TO ADD A NEW SENSOR:
* Step 1 — Write a float function that reads the sensor value
* Step 2 — Add one row to the SENSORS[] table below
* That's it. No other code needs to change.
*
* BOARD : NodeMCU 1.0 (ESP-12E Module)
* LIBRARIES (Arduino Library Manager):
* • ESP8266WiFi — part of ESP8266 board package
* • ESP8266HTTPClient — part of ESP8266 board package
* • ArduinoJson — by Benoit Blanchon v6.x
*
* SERIAL MONITOR: 115200 baud
* ════════════════════════════════════════════════════════════════
*/
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClientSecureBearSSL.h>
#include <ArduinoJson.h>
// ── STEP 0 — Server & credentials ────────────────────────────────
const char* WIFI_SSID = "Your-SSID";
const char* WIFI_PASSWORD = "Your-Password";
const char* API_KEY = ""; // from dashboard → API Key pill
// Production server (HTTPS)
const char* SERVER = "https://iot.getyourprojectdone.in";
// Local LAMPP testing — comment out SERVER above, uncomment this:
// const char* SERVER = "http://192.168.x.x/iot_platform";
// Send interval (milliseconds)
const unsigned long SEND_INTERVAL = 10000; // 10 seconds
// ─────────────────────────────────────────────────────────────────
// ════════════════════════════════════════════════════════════════
// STEP 1 — Write one float function per sensor
// Replace the simulated return values with real sensor reads.
// See sensor_library.h (accessory file) for copy-paste examples
// for DHT11, HC-SR04, MQ-2, BMP280, DS18B20, LDR, and more.
// ════════════════════════════════════════════════════════════════
float readTemperature() {
// TODO: e.g. return dht.readTemperature();
return 28.5;
}
float readHumidity() {
// TODO: e.g. return dht.readHumidity();
return 62.0;
}
float readGas() {
// TODO: e.g. return analogRead(A0) * (5.0/1023.0) * 100;
return 350.0;
}
float readDistance() {
// TODO: e.g. return ultrasonicCm(TRIG_PIN, ECHO_PIN);
return 120.0;
}
// ════════════════════════════════════════════════════════════════
// STEP 2 — Register sensors in this table
// Add or remove rows freely — nothing else needs to change.
//
// Columns:
// "device_name" — must EXACTLY match name on Devices page
// "sensor_type" — temperature | humidity | gas | distance |
// pressure | light | ph | co2 | motion | custom
// "unit" — C | F | % | ppm | cm | hPa | lux | V | etc.
// readFunction — the function you wrote in Step 1
// ════════════════════════════════════════════════════════════════
struct Sensor {
const char* deviceName;
const char* type;
const char* unit;
float (*readFn)();
};
Sensor SENSORS[] = {
// { "device_name", "sensor_type", "unit", readFunction }
{ "temp_sensor", "temperature", "C", readTemperature },
{ "hum_sensor", "humidity", "%", readHumidity },
{ "gas_sensor", "gas", "ppm", readGas },
{ "ultra_sensor", "distance", "cm", readDistance },
// Add more rows here — copy the format above
};
// ─────────────────────────────────────────────────────────────────
// Internals — no changes needed below this line
// ─────────────────────────────────────────────────────────────────
const int SENSOR_COUNT = sizeof(SENSORS) / sizeof(SENSORS[0]);
BearSSL::WiFiClientSecure secureClient;
WiFiClient plainClient;
unsigned long lastSend = 0;
int cycleNum = 0;
void setup() {
Serial.begin(115200);
delay(300);
Serial.println(F("\n══════════════════════════════════"));
Serial.println(F(" ESP8266 Multi-Sensor Monitor"));
Serial.printf( " Sensors registered : %d\n", SENSOR_COUNT);
Serial.printf( " Send interval : %lu ms\n", SEND_INTERVAL);
Serial.println(F("══════════════════════════════════\n"));
secureClient.setInsecure(); // skip SSL cert verification (fine for IoT)
connectWiFi();
lastSend = millis() - SEND_INTERVAL; // send immediately on first loop
}
void loop() {
if (WiFi.status() != WL_CONNECTED) {
Serial.println(F("[WiFi] Disconnected — reconnecting..."));
connectWiFi();
return;
}
if (millis() - lastSend >= SEND_INTERVAL) {
lastSend = millis();
cycleNum++;
Serial.printf("\n─── Cycle #%d ───────────────────────\n", cycleNum);
sendAllSensors();
}
}
// ── Build JSON and POST all sensors in one request ────────────────
void sendAllSensors() {
// Read all sensor values first
float values[SENSOR_COUNT];
for (int i = 0; i < SENSOR_COUNT; i++) {
values[i] = SENSORS[i].readFn();
if (isnan(values[i])) {
Serial.printf("[Sensor] WARNING: %s returned NaN — skipping\n", SENSORS[i].deviceName);
values[i] = -999;
}
Serial.printf("[Sensor] %-16s = %.2f %s\n",
SENSORS[i].deviceName, values[i], SENSORS[i].unit);
}
// Build JSON: { "api_key":"...", "devices":[{...},{...},...] }
DynamicJsonDocument doc(512 + SENSOR_COUNT * 120);
doc["api_key"] = API_KEY;
JsonArray devices = doc.createNestedArray("devices");
for (int i = 0; i < SENSOR_COUNT; i++) {
if (values[i] == -999) continue; // skip failed reads
JsonObject device = devices.createNestedObject();
device["device_name"] = SENSORS[i].deviceName;
JsonArray sensors = device.createNestedArray("sensors");
JsonObject sensor = sensors.createNestedObject();
sensor["type"] = SENSORS[i].type;
sensor["value"] = String(values[i], 2); // 2 decimal places
sensor["unit"] = SENSORS[i].unit;
}
String payload;
serializeJson(doc, payload);
// POST request
String url = String(SERVER) + "/api/insert_data.php";
String resp = httpPost(url, payload);
if (resp.isEmpty()) {
Serial.println(F("[HTTP] No response — check SERVER and network"));
return;
}
// Parse response
StaticJsonDocument<256> rdoc;
if (deserializeJson(rdoc, resp) == DeserializationError::Ok) {
const char* status = rdoc["status"] | "error";
const char* msg = rdoc["message"] | "";
if (strcmp(status, "success") == 0) {
Serial.printf("[Server] OK — %s\n", msg);
} else {
Serial.printf("[Server] ERROR — %s\n", msg);
if (rdoc.containsKey("errors")) {
for (const char* e : rdoc["errors"].as<JsonArray>())
Serial.printf(" • %s\n", e);
}
}
} else {
Serial.printf("[Server] Raw: %s\n", resp.c_str());
}
}
// ── HTTP POST helper ──────────────────────────────────────────────
String httpPost(const String& url, const String& body) {
bool isHttps = url.startsWith("https");
HTTPClient http;
if (isHttps) {
http.begin(secureClient, url);
} else {
http.begin(plainClient, url);
}
http.addHeader(F("Content-Type"), F("application/json"));
http.setTimeout(10000);
int code = http.POST(body);
String response = "";
if (code > 0) {
response = http.getString();
if (code != 200)
Serial.printf("[HTTP] Code: %d\n", code);
} else {
Serial.printf("[HTTP] Failed: %s\n", http.errorToString(code).c_str());
}
http.end();
return response;
}
// ── WiFi ──────────────────────────────────────────────────────────
void connectWiFi() {
Serial.printf("[WiFi] Connecting to %s", WIFI_SSID);
WiFi.mode(WIFI_STA);
WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
int t = 0;
while (WiFi.status() != WL_CONNECTED && t < 40) {
delay(500); Serial.print('.'); t++;
}
if (WiFi.status() == WL_CONNECTED) {
Serial.println(F(" connected!"));
Serial.printf("[WiFi] IP: %s Signal: %d dBm\n",
WiFi.localIP().toString().c_str(), WiFi.RSSI());
} else {
Serial.println(F(" FAILED — check SSID/password"));
}
}
esp8266_control.ino
/*
* ════════════════════════════════════════════════════════════════
* ESP8266 — Multi-Device Control | IoT Platform
* Production-ready • Add unlimited control devices in 2 steps
* ════════════════════════════════════════════════════════════════
*
* HOW IT WORKS:
* 1. Every POLL_INTERVAL ms → asks server for pending commands
* 2. Executes each command on the correct GPIO / pin
* 3. Acknowledges each command back to the server
*
* HOW TO ADD A NEW CONTROL DEVICE:
* Step 1 — Write a handler void function for the device
* Step 2 — Add one row to DEVICES[] table below
*
* BOARD : NodeMCU 1.0 (ESP-12E Module)
* LIBRARIES: ESP8266WiFi, ESP8266HTTPClient, ArduinoJson v6.x
* SERIAL MONITOR: 115200 baud
* ════════════════════════════════════════════════════════════════
*/
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <WiFiClientSecureBearSSL.h>
#include <ArduinoJson.h>
// ── STEP 0 — Credentials & server ────────────────────────────────
const char* WIFI_SSID = "Your-SSID";
const char* WIFI_PASSWORD = "Your-Password";
const char* API_KEY = "";
// Production server (HTTPS)
const char* SERVER = "https://iot.getyourprojectdone.in";
// Local LAMPP testing:
// const char* SERVER = "http://192.168.x.x/iot_platform";
const unsigned long POLL_INTERVAL = 5000; // poll commands every 5 s
// ─────────────────────────────────────────────────────────────────
// ════════════════════════════════════════════════════════════════
// STEP 1 — Define pins and write one handler per control device
//
// Command types sent by the dashboard:
// "ON" → switch ON (relay, LED, fan, buzzer …)
// "OFF" → switch OFF
// "SET_VALUE" → set to a value (dimmer %, servo angle, PWM …)
// cmdValue = the numeric string e.g. "75"
//
// Handler signature: void myHandler(const char* type, const char* value)
// ════════════════════════════════════════════════════════════════
// ── Built-in LED (D4 / GPIO2, active LOW) ────────────────────────
#define PIN_LED LED_BUILTIN // D4
void handleLED(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { digitalWrite(PIN_LED, LOW); Serial.println(F("[LED] ON")); }
if (strcmp(type, "OFF") == 0) { digitalWrite(PIN_LED, HIGH); Serial.println(F("[LED] OFF")); }
}
// ── Relay (active HIGH — connect relay IN pin here) ───────────────
#define PIN_RELAY D1 // GPIO5
void handleRelay(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { digitalWrite(PIN_RELAY, HIGH); Serial.println(F("[Relay] ON")); }
if (strcmp(type, "OFF") == 0) { digitalWrite(PIN_RELAY, LOW); Serial.println(F("[Relay] OFF")); }
}
// ── Fan / Motor (PWM speed control via SET_VALUE 0-100) ──────────
#define PIN_FAN D2 // GPIO4 — must be PWM-capable
void handleFan(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { analogWrite(PIN_FAN, 255); Serial.println(F("[Fan] FULL ON")); }
if (strcmp(type, "OFF") == 0) { analogWrite(PIN_FAN, 0); Serial.println(F("[Fan] OFF")); }
if (strcmp(type, "SET_VALUE") == 0) {
int pct = constrain(atoi(val), 0, 100);
int pwm = map(pct, 0, 100, 0, 255);
analogWrite(PIN_FAN, pwm);
Serial.printf("[Fan] Speed = %d%%\n", pct);
}
}
// ── Servo (SET_VALUE = angle 0-180) ──────────────────────────────
// #include <Servo.h>
// Servo myServo;
// #define PIN_SERVO D5
// void handleServo(const char* type, const char* val) {
// if (strcmp(type, "SET_VALUE") == 0) {
// int angle = constrain(atoi(val), 0, 180);
// myServo.write(angle);
// Serial.printf("[Servo] Angle = %d\n", angle);
// }
// if (strcmp(type, "ON") == 0) { myServo.write(180); }
// if (strcmp(type, "OFF") == 0) { myServo.write(0); }
// }
// ── Buzzer (ON/OFF or SET_VALUE = frequency Hz) ───────────────────
// #define PIN_BUZZER D6
// void handleBuzzer(const char* type, const char* val) {
// if (strcmp(type, "ON") == 0) { tone(PIN_BUZZER, 1000); }
// if (strcmp(type, "OFF") == 0) { noTone(PIN_BUZZER); }
// if (strcmp(type, "SET_VALUE") == 0) { tone(PIN_BUZZER, atoi(val)); }
// }
// ════════════════════════════════════════════════════════════════
// STEP 2 — Register control devices in this table
// "device_name" must EXACTLY match the name on your Devices page
// (Device Type must be a control type: relay, led, fan, servo …)
// ════════════════════════════════════════════════════════════════
struct ControlDevice {
const char* deviceName;
void (*handler)(const char* cmdType, const char* cmdValue);
};
ControlDevice DEVICES[] = {
// { "device_name", handlerFunction }
{ "led", handleLED },
{ "relay", handleRelay },
{ "fan", handleFan },
// Uncomment to add:
// { "servo", handleServo },
// { "buzzer", handleBuzzer },
};
// ─────────────────────────────────────────────────────────────────
// Internals — no changes needed below this line
// ─────────────────────────────────────────────────────────────────
const int DEVICE_COUNT = sizeof(DEVICES) / sizeof(DEVICES[0]);
BearSSL::WiFiClientSecure secureClient;
WiFiClient plainClient;
unsigned long lastPoll = 0;
void setup() {
Serial.begin(115200);
delay(300);
Serial.println(F("\n══════════════════════════════════"));
Serial.println(F(" ESP8266 Multi-Device Control"));
Serial.printf( " Devices registered : %d\n", DEVICE_COUNT);
Serial.printf( " Poll interval : %lu ms\n", POLL_INTERVAL);
Serial.println(F("══════════════════════════════════\n"));
// Init all control pins
pinMode(PIN_LED, OUTPUT); digitalWrite(PIN_LED, HIGH); // LED off
pinMode(PIN_RELAY, OUTPUT); digitalWrite(PIN_RELAY, LOW); // Relay off
pinMode(PIN_FAN, OUTPUT); analogWrite(PIN_FAN, 0); // Fan off
secureClient.setInsecure();
connectWiFi();
lastPoll = millis() - POLL_INTERVAL;
}
void loop() {
if (WiFi.status() != WL_CONNECTED) {
Serial.println(F("[WiFi] Disconnected — reconnecting..."));
connectWiFi();
return;
}
if (millis() - lastPoll >= POLL_INTERVAL) {
lastPoll = millis();
pollAllDevices();
}
}
// ── Poll commands for every registered device ─────────────────────
void pollAllDevices() {
for (int i = 0; i < DEVICE_COUNT; i++) {
pollDevice(DEVICES[i].deviceName, DEVICES[i].handler);
}
}
void pollDevice(const char* deviceName, void(*handler)(const char*, const char*)) {
// Build poll request
StaticJsonDocument<128> req;
req["api_key"] = API_KEY;
req["device_name"] = deviceName;
String payload;
serializeJson(req, payload);
String url = String(SERVER) + "/api/device_poll.php";
String resp = httpPost(url, payload);
if (resp.isEmpty()) return;
StaticJsonDocument<1024> doc;
if (deserializeJson(doc, resp) != DeserializationError::Ok) return;
if (strcmp(doc["status"] | "error", "success") != 0) {
Serial.printf("[Poll] %s — %s\n", deviceName, doc["message"] | "error");
return;
}
JsonArray cmds = doc["commands"].as<JsonArray>();
if (cmds.size() == 0) return;
Serial.printf("[Poll] %s — %d command(s)\n", deviceName, (int)cmds.size());
for (JsonObject cmd : cmds) {
int id = cmd["id"] | 0;
const char* type = cmd["command_type"] | "";
const char* val = cmd["command_value"] | "";
Serial.printf("[CMD] #%d %s → type=%s value=%s\n", id, deviceName, type, val);
handler(type, val);
ackCommand(id, "executed");
delay(50);
}
}
// ── Acknowledge a command ─────────────────────────────────────────
void ackCommand(int cmdId, const char* status) {
StaticJsonDocument<128> doc;
doc["api_key"] = API_KEY;
doc["command_id"] = cmdId;
doc["status"] = status;
String payload;
serializeJson(doc, payload);
String url = String(SERVER) + "/api/device_ack.php";
String resp = httpPost(url, payload);
if (!resp.isEmpty()) {
StaticJsonDocument<128> rdoc;
deserializeJson(rdoc, resp);
Serial.printf("[Ack] #%d → %s\n", cmdId, rdoc["message"] | resp.c_str());
}
}
// ── HTTP POST helper ──────────────────────────────────────────────
String httpPost(const String& url, const String& body) {
bool isHttps = url.startsWith("https");
HTTPClient http;
if (isHttps) http.begin(secureClient, url);
else http.begin(plainClient, url);
http.addHeader(F("Content-Type"), F("application/json"));
http.setTimeout(8000);
int code = http.POST(body);
String response = "";
if (code > 0) {
response = http.getString();
} else {
Serial.printf("[HTTP] Error: %s\n", http.errorToString(code).c_str());
}
http.end();
return response;
}
// ── WiFi ──────────────────────────────────────────────────────────
void connectWiFi() {
Serial.printf("[WiFi] Connecting to %s", WIFI_SSID);
WiFi.mode(WIFI_STA);
WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
int t = 0;
while (WiFi.status() != WL_CONNECTED && t < 40) {
delay(500); Serial.print('.'); t++;
}
if (WiFi.status() == WL_CONNECTED) {
Serial.println(F(" connected!"));
Serial.printf("[WiFi] IP: %s\n", WiFi.localIP().toString().c_str());
} else {
Serial.println(F(" FAILED"));
}
}
Board: Arduino Uno / Mega with ESP8266 via SoftwareSerial (D2/D3) |
Library: WiFiEsp by bportaluri |
Baud: 9600
ardiuno_monitor.ino
/*
* ════════════════════════════════════════════════════════════════
* Arduino Uno/Mega + ESP8266 Module — Multi-Sensor Monitor
* Production-ready • Add unlimited sensors in 2 steps
* ════════════════════════════════════════════════════════════════
*
* WIRING (ESP8266 as serial WiFi via AT commands):
* Arduino D2 → ESP8266 TX
* Arduino D3 → ESP8266 RX (use 3.3 V level-shifter)
* ESP8266 VCC → 3.3 V (NOT 5 V — will damage module)
* ESP8266 GND → GND
* ESP8266 CH_EN → 3.3 V
*
* HOW TO ADD A NEW SENSOR:
* Step 1 — Write a float function that reads the sensor value
* Step 2 — Add one row to the SENSORS[] table below
*
* LIBRARY: WiFiEsp by bportaluri (Arduino Library Manager)
* SERIAL MONITOR: 9600 baud
* ════════════════════════════════════════════════════════════════
*/
#include <WiFiEsp.h>
#include <SoftwareSerial.h>
// ── STEP 0 — Credentials & server ────────────────────────────────
const char* WIFI_SSID = "Your-SSID";
const char* WIFI_PASSWORD = "Your-Password";
const char* API_KEY = "";
// Production server
const char* SERVER_HOST = "iot.getyourprojectdone.in";
const int SERVER_PORT = 443; // 443 = HTTPS/SSL
// Local LAMPP: SERVER_HOST = "192.168.x.x"; SERVER_PORT = 80;
// API path on the server
const char* API_PATH = "/api/insert_data.php";
// Local LAMPP: const char* API_PATH = "/iot_platform/api/insert_data.php";
const unsigned long SEND_INTERVAL = 15000; // 15 seconds (AT commands are slower)
// ─────────────────────────────────────────────────────────────────
// ════════════════════════════════════════════════════════════════
// STEP 1 — Write one float function per sensor
// ════════════════════════════════════════════════════════════════
float readTemperature() {
// TODO: e.g. return dht.readTemperature();
return 27.5;
}
float readHumidity() {
// TODO: e.g. return dht.readHumidity();
return 58.0;
}
float readGas() {
// TODO: e.g. return analogRead(A0) * (5.0 / 1023.0) * 100;
return 380.0;
}
float readDistance() {
// TODO: e.g. ultrasonic pulseIn measurement
return 100.0;
}
// ════════════════════════════════════════════════════════════════
// STEP 2 — Register sensors in this table
// "device_name" must EXACTLY match name on your Devices page
// ════════════════════════════════════════════════════════════════
struct Sensor {
const char* deviceName;
const char* type;
const char* unit;
float (*readFn)();
};
Sensor SENSORS[] = {
// { "device_name", "sensor_type", "unit", readFunction }
{ "temp_sensor", "temperature", "C", readTemperature },
{ "hum_sensor", "humidity", "%", readHumidity },
{ "gas_sensor", "gas", "ppm", readGas },
{ "ultra_sensor", "distance", "cm", readDistance },
};
// ─────────────────────────────────────────────────────────────────
// Internals
// ─────────────────────────────────────────────────────────────────
const int SENSOR_COUNT = sizeof(SENSORS) / sizeof(SENSORS[0]);
SoftwareSerial espSerial(2, 3); // RX=D2, TX=D3
WiFiEspClient client;
unsigned long lastSend = 0;
int cycleNum = 0;
void setup() {
Serial.begin(9600);
espSerial.begin(9600);
delay(2000);
Serial.println(F("\n══════════════════════════════════"));
Serial.println(F(" Arduino Multi-Sensor Monitor"));
Serial.print(F(" Sensors: ")); Serial.println(SENSOR_COUNT);
Serial.println(F("══════════════════════════════════\n"));
WiFiEsp.init(&espSerial);
if (WiFiEsp.status() == WL_NO_SHIELD) {
Serial.println(F("[ERROR] ESP8266 not detected — check wiring"));
while (true);
}
connectWiFi();
lastSend = millis() - SEND_INTERVAL;
}
void loop() {
if (WiFiEsp.status() != WL_CONNECTED) {
Serial.println(F("[WiFi] Reconnecting..."));
connectWiFi();
return;
}
if (millis() - lastSend >= SEND_INTERVAL) {
lastSend = millis();
cycleNum++;
Serial.print(F("\n─── Cycle #")); Serial.print(cycleNum); Serial.println(F(" ───"));
sendAllSensors();
}
}
// ── Build JSON and POST ───────────────────────────────────────────
void sendAllSensors() {
float values[SENSOR_COUNT];
for (int i = 0; i < SENSOR_COUNT; i++) {
values[i] = SENSORS[i].readFn();
Serial.print(F("[Sensor] ")); Serial.print(SENSORS[i].deviceName);
Serial.print(F(" = ")); Serial.print(values[i]); Serial.println(SENSORS[i].unit);
}
// Build JSON manually (no ArduinoJson on Uno — saves RAM)
String json = F("{\"api_key\":\"");
json += API_KEY;
json += F("\",\"devices\":[");
for (int i = 0; i < SENSOR_COUNT; i++) {
if (i > 0) json += ',';
json += F("{\"device_name\":\"");
json += SENSORS[i].deviceName;
json += F("\",\"sensors\":[{\"type\":\"");
json += SENSORS[i].type;
json += F("\",\"value\":\"");
json += String(values[i], 2);
json += F("\",\"unit\":\"");
json += SENSORS[i].unit;
json += F("\"}]}");
}
json += F("]}");
Serial.print(F("[HTTP] Payload length: ")); Serial.println(json.length());
sendPost(json);
}
// ── AT-command HTTP/HTTPS POST ────────────────────────────────────
void sendPost(const String& json) {
bool useSSL = (SERVER_PORT == 443);
// Build HTTP request string
String request = F("POST ");
request += API_PATH;
request += F(" HTTP/1.1\r\nHost: ");
request += SERVER_HOST;
request += F("\r\nContent-Type: application/json\r\nContent-Length: ");
request += json.length();
request += F("\r\nConnection: close\r\n\r\n");
request += json;
// Connect via SSL or TCP
int ok;
if (useSSL) {
ok = client.connectSSL(SERVER_HOST, SERVER_PORT);
} else {
ok = client.connect(SERVER_HOST, SERVER_PORT);
}
if (!ok) {
Serial.println(F("[HTTP] Connection failed"));
return;
}
client.print(request);
Serial.println(F("[HTTP] Request sent — reading response..."));
// Read response (skip headers, grab body)
String body = "";
bool inBody = false;
unsigned long t = millis();
while ((client.connected() || client.available()) && millis() - t < 8000) {
while (client.available()) {
String line = client.readStringUntil('\n');
if (!inBody && line == "\r") { inBody = true; continue; }
if (inBody) { body += line; }
}
}
client.stop();
body.trim();
Serial.print(F("[Server] ")); Serial.println(body.isEmpty() ? F("(no body)") : body.c_str());
}
// ── WiFi ──────────────────────────────────────────────────────────
void connectWiFi() {
Serial.print(F("[WiFi] Connecting to "));
Serial.print(WIFI_SSID);
int status = WL_IDLE_STATUS;
int tries = 0;
while (status != WL_CONNECTED && tries < 10) {
status = WiFiEsp.begin(WIFI_SSID, WIFI_PASSWORD);
Serial.print('.');
tries++;
}
if (WiFiEsp.status() == WL_CONNECTED) {
Serial.println(F(" connected!"));
Serial.print(F("[WiFi] IP: "));
Serial.println(WiFiEsp.localIP());
} else {
Serial.println(F(" FAILED — check SSID/password or ESP8266 baud rate"));
}
}
ardiuno_control.ino
/*
* ════════════════════════════════════════════════════════════════
* Arduino Uno/Mega + ESP8266 Module — Multi-Device Control
* Production-ready • Add unlimited control devices in 2 steps
* ════════════════════════════════════════════════════════════════
*
* WIRING:
* Arduino D2 → ESP8266 TX | Arduino D3 → ESP8266 RX
* ESP8266 VCC → 3.3 V | ESP8266 GND → GND
* ESP8266 CH_EN → 3.3 V
*
* HOW TO ADD A NEW CONTROL DEVICE:
* Step 1 — Write a void handler function for the device
* Step 2 — Add one row to DEVICES[] table below
*
* LIBRARY: WiFiEsp by bportaluri (Library Manager)
* SERIAL MONITOR: 9600 baud
* ════════════════════════════════════════════════════════════════
*/
#include <WiFiEsp.h>
#include <SoftwareSerial.h>
// ── STEP 0 — Credentials & server ────────────────────────────────
const char* WIFI_SSID = "Your-SSID";
const char* WIFI_PASSWORD = "Your-Password";
const char* API_KEY = "";
const char* SERVER_HOST = "iot.getyourprojectdone.in";
const int SERVER_PORT = 443;
// Local LAMPP: SERVER_HOST = "192.168.x.x"; SERVER_PORT = 80;
const char* POLL_PATH = "/api/device_poll.php";
const char* ACK_PATH = "/api/device_ack.php";
// Local LAMPP:
// const char* POLL_PATH = "/iot_platform/api/device_poll.php";
// const char* ACK_PATH = "/iot_platform/api/device_ack.php";
const unsigned long POLL_INTERVAL = 8000; // poll every 8 s
// ─────────────────────────────────────────────────────────────────
// ════════════════════════════════════════════════════════════════
// STEP 1 — Define pins and write one handler per device
//
// Handler receives: cmdType ("ON" | "OFF" | "SET_VALUE")
// cmdValue (numeric string, e.g. "75")
// ════════════════════════════════════════════════════════════════
// ── Built-in LED (pin 13, active HIGH on most Arduino boards) ────
#define PIN_LED 13
void handleLED(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { digitalWrite(PIN_LED, HIGH); Serial.println(F("[LED] ON")); }
if (strcmp(type, "OFF") == 0) { digitalWrite(PIN_LED, LOW); Serial.println(F("[LED] OFF")); }
}
// ── Relay (active HIGH) ───────────────────────────────────────────
#define PIN_RELAY 7
void handleRelay(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { digitalWrite(PIN_RELAY, HIGH); Serial.println(F("[Relay] ON")); }
if (strcmp(type, "OFF") == 0) { digitalWrite(PIN_RELAY, LOW); Serial.println(F("[Relay] OFF")); }
}
// ── Fan via PWM (SET_VALUE = 0-100 percent) ───────────────────────
// Arduino Uno PWM pins: 3,5,6,9,10,11
#define PIN_FAN 9
void handleFan(const char* type, const char* val) {
if (strcmp(type, "ON") == 0) { analogWrite(PIN_FAN, 255); Serial.println(F("[Fan] FULL ON")); }
if (strcmp(type, "OFF") == 0) { analogWrite(PIN_FAN, 0); Serial.println(F("[Fan] OFF")); }
if (strcmp(type, "SET_VALUE") == 0) {
int pct = constrain(atoi(val), 0, 100);
analogWrite(PIN_FAN, map(pct, 0, 100, 0, 255));
Serial.print(F("[Fan] Speed = ")); Serial.print(pct); Serial.println('%');
}
}
// ── Buzzer (ON/OFF or SET_VALUE = duration ms) ────────────────────
// #define PIN_BUZZER 6
// void handleBuzzer(const char* type, const char* val) {
// if (strcmp(type, "ON") == 0) { digitalWrite(PIN_BUZZER, HIGH); }
// if (strcmp(type, "OFF") == 0) { digitalWrite(PIN_BUZZER, LOW); }
// if (strcmp(type, "SET_VALUE") == 0) {
// digitalWrite(PIN_BUZZER, HIGH);
// delay(atoi(val));
// digitalWrite(PIN_BUZZER, LOW);
// }
// }
// ════════════════════════════════════════════════════════════════
// STEP 2 — Register devices in this table
// ════════════════════════════════════════════════════════════════
struct ControlDevice {
const char* deviceName;
void (*handler)(const char* cmdType, const char* cmdValue);
};
ControlDevice DEVICES[] = {
// { "device_name", handlerFunction }
{ "led", handleLED },
{ "relay", handleRelay },
{ "fan", handleFan },
// Uncomment to add:
// { "buzzer", handleBuzzer },
};
// ─────────────────────────────────────────────────────────────────
// Internals
// ─────────────────────────────────────────────────────────────────
const int DEVICE_COUNT = sizeof(DEVICES) / sizeof(DEVICES[0]);
SoftwareSerial espSerial(2, 3);
WiFiEspClient client;
unsigned long lastPoll = 0;
void setup() {
Serial.begin(9600);
espSerial.begin(9600);
delay(2000);
Serial.println(F("\n══════════════════════════════════"));
Serial.println(F(" Arduino Multi-Device Control"));
Serial.print(F(" Devices : ")); Serial.println(DEVICE_COUNT);
Serial.println(F("══════════════════════════════════\n"));
pinMode(PIN_LED, OUTPUT); digitalWrite(PIN_LED, LOW);
pinMode(PIN_RELAY, OUTPUT); digitalWrite(PIN_RELAY, LOW);
pinMode(PIN_FAN, OUTPUT); analogWrite(PIN_FAN, 0);
WiFiEsp.init(&espSerial);
if (WiFiEsp.status() == WL_NO_SHIELD) {
Serial.println(F("[ERROR] ESP8266 not detected"));
while (true);
}
connectWiFi();
lastPoll = millis() - POLL_INTERVAL;
}
void loop() {
if (WiFiEsp.status() != WL_CONNECTED) {
connectWiFi(); return;
}
if (millis() - lastPoll >= POLL_INTERVAL) {
lastPoll = millis();
for (int i = 0; i < DEVICE_COUNT; i++) {
pollDevice(DEVICES[i].deviceName, DEVICES[i].handler);
}
}
}
// ── Poll one device ───────────────────────────────────────────────
void pollDevice(const char* devName, void(*handler)(const char*, const char*)) {
// Build request JSON
String json = F("{\"api_key\":\"");
json += API_KEY;
json += F("\",\"device_name\":\"");
json += devName;
json += F("\"}");
String resp = doPost(POLL_PATH, json);
if (resp.isEmpty()) return;
// Find "commands" array manually (avoids ArduinoJson RAM on Uno)
// If response contains "command_type" there are commands
if (resp.indexOf(F("command_type")) == -1) return;
Serial.print(F("[Poll] ")); Serial.print(devName);
Serial.println(F(" — commands found"));
// Parse up to 5 commands
int searchFrom = 0;
for (int c = 0; c < 5; c++) {
int idIdx = resp.indexOf(F("\"id\":"), searchFrom);
if (idIdx == -1) break;
// Extract id
int idStart = idIdx + 5;
int idEnd = resp.indexOf(',', idStart);
int cmdId = resp.substring(idStart, idEnd).toInt();
// Extract command_type
int typeIdx = resp.indexOf(F("\"command_type\":\""), searchFrom);
if (typeIdx == -1) break;
int tStart = typeIdx + 16;
int tEnd = resp.indexOf('"', tStart);
String cmdType = resp.substring(tStart, tEnd);
// Extract command_value
int valIdx = resp.indexOf(F("\"command_value\":\""), searchFrom);
int vStart = valIdx + 17;
int vEnd = resp.indexOf('"', vStart);
String cmdVal = (valIdx != -1) ? resp.substring(vStart, vEnd) : "";
Serial.print(F("[CMD] #")); Serial.print(cmdId);
Serial.print(F(" type=")); Serial.print(cmdType);
Serial.print(F(" value=")); Serial.println(cmdVal);
handler(cmdType.c_str(), cmdVal.c_str());
ackCommand(cmdId, "executed");
// Move search cursor past this command
searchFrom = tEnd + 1;
delay(100);
}
}
// ── Acknowledge command ───────────────────────────────────────────
void ackCommand(int cmdId, const char* status) {
String json = F("{\"api_key\":\"");
json += API_KEY;
json += F("\",\"command_id\":");
json += cmdId;
json += F(",\"status\":\"");
json += status;
json += F("\"}");
String resp = doPost(ACK_PATH, json);
Serial.print(F("[Ack] #")); Serial.print(cmdId);
Serial.print(F(" → "));
Serial.println(resp.isEmpty() ? F("no response") : resp.c_str());
}
// ── AT-command POST (SSL or plain HTTP) ──────────────────────────
String doPost(const char* path, const String& json) {
bool useSSL = (SERVER_PORT == 443);
String request = F("POST ");
request += path;
request += F(" HTTP/1.1\r\nHost: ");
request += SERVER_HOST;
request += F("\r\nContent-Type: application/json\r\nContent-Length: ");
request += json.length();
request += F("\r\nConnection: close\r\n\r\n");
request += json;
int ok = useSSL ? client.connectSSL(SERVER_HOST, SERVER_PORT)
: client.connect(SERVER_HOST, SERVER_PORT);
if (!ok) { Serial.println(F("[HTTP] Connect failed")); return ""; }
client.print(request);
String body = "";
bool inBody = false;
unsigned long t = millis();
while ((client.connected() || client.available()) && millis() - t < 8000) {
while (client.available()) {
String line = client.readStringUntil('\n');
if (!inBody && line == "\r") { inBody = true; continue; }
if (inBody) body += line;
}
}
client.stop();
body.trim();
return body;
}
// ── WiFi ──────────────────────────────────────────────────────────
void connectWiFi() {
Serial.print(F("[WiFi] Connecting"));
int status = WL_IDLE_STATUS, tries = 0;
while (status != WL_CONNECTED && tries < 10) {
status = WiFiEsp.begin(WIFI_SSID, WIFI_PASSWORD);
Serial.print('.'); tries++;
}
if (WiFiEsp.status() == WL_CONNECTED) {
Serial.println(F(" connected!"));
Serial.print(F("[WiFi] IP: ")); Serial.println(WiFiEsp.localIP());
} else {
Serial.println(F(" FAILED"));
}
}
Board: Raspberry Pi Pico W |
Runtime: MicroPython (flash firmware first) |
Tool: Thonny IDE or rshell
raspberry_monitor.py
"""
════════════════════════════════════════════════════════════════
Raspberry Pi Pico W — Multi-Sensor Monitor (MicroPython)
Production-ready • Add unlimited sensors in 2 steps
════════════════════════════════════════════════════════════════
HOW TO ADD A NEW SENSOR:
Step 1 — Write a function that returns a float value
Step 2 — Add one dict to the SENSORS list below
FIRMWARE: MicroPython for Pico W
https://micropython.org/download/rp2-pico-w/
NOTE: For a full Raspberry Pi (Linux/Raspbian), see the note
at the bottom of this file — uses the standard `requests` lib.
════════════════════════════════════════════════════════════════
"""
import network
import urequests
import ujson
import utime
# ── STEP 0 — Credentials & server ────────────────────────────────
WIFI_SSID = "Your-SSID"
WIFI_PASSWORD = "Your-Password"
API_KEY = "" # from dashboard → API Key pill
# Production server (HTTPS)
SERVER = "https://iot.getyourprojectdone.in"
# Local LAMPP testing — comment out SERVER above, use this:
# SERVER = "http://192.168.x.x/iot_platform"
SEND_INTERVAL = 10 # seconds between sends
# ─────────────────────────────────────────────────────────────────
# ════════════════════════════════════════════════════════════════
# STEP 1 — Write one function per sensor.
# Each function must return a float.
# Replace the simulated values with real sensor reads.
# See the SENSOR SNIPPETS section at the bottom for DHT11,
# DS18B20, BMP280, HC-SR04, MQ-2, LDR, and more.
# ════════════════════════════════════════════════════════════════
def read_temperature():
# TODO: e.g. from machine import ADC (onboard sensor)
# or use DHT11/DHT22 library
return 27.5 # simulated
def read_humidity():
# TODO: e.g. dht_sensor.humidity()
return 62.0 # simulated
def read_gas():
# TODO: e.g. ADC(26).read_u16() / 65535 * 100
return 350.0 # simulated
def read_distance():
# TODO: HC-SR04 pulse measurement
return 115.0 # simulated
# ════════════════════════════════════════════════════════════════
# STEP 2 — Register sensors in this list.
# Add or remove dicts freely — nothing else needs to change.
#
# Keys:
# "device" — must EXACTLY match name on your Devices page
# "type" — temperature | humidity | gas | distance |
# pressure | light | ph | co2 | motion | custom
# "unit" — C | F | % | ppm | cm | hPa | lux | V | etc.
# "fn" — the function you wrote in Step 1
# ════════════════════════════════════════════════════════════════
SENSORS = [
# { "device": "device_name", "type": "sensor_type", "unit": "unit", "fn": read_function },
{ "device": "temp_sensor", "type": "temperature", "unit": "C", "fn": read_temperature },
{ "device": "hum_sensor", "type": "humidity", "unit": "%", "fn": read_humidity },
{ "device": "gas_sensor", "type": "gas", "unit": "ppm", "fn": read_gas },
{ "device": "ultra_sensor", "type": "distance", "unit": "cm", "fn": read_distance },
# Add more dicts here:
# { "device": "pressure_sensor", "type": "pressure", "unit": "hPa", "fn": read_pressure },
]
# ─────────────────────────────────────────────────────────────────
# Internals — no changes needed below this line
# ─────────────────────────────────────────────────────────────────
def connect_wifi():
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
if wlan.isconnected():
return wlan
print(f"[WiFi] Connecting to {WIFI_SSID}", end="")
wlan.connect(WIFI_SSID, WIFI_PASSWORD)
for _ in range(30):
if wlan.isconnected():
break
utime.sleep(1)
print(".", end="")
if wlan.isconnected():
print(f" connected!\n[WiFi] IP: {wlan.ifconfig()[0]}")
else:
print("\n[WiFi] FAILED — check SSID/password")
return wlan
def send_all_sensors():
# Read all values
readings = []
for s in SENSORS:
try:
val = s["fn"]()
readings.append((s, round(float(val), 2)))
print(f"[Sensor] {s['device']:<18} = {val} {s['unit']}")
except Exception as e:
print(f"[Sensor] {s['device']} ERROR: {e}")
if not readings:
print("[Send] No valid readings — skipping")
return
# Build payload
payload = {
"api_key": API_KEY,
"devices": [
{
"device_name": s["device"],
"sensors": [
{
"type": s["type"],
"value": str(val),
"unit": s["unit"]
}
]
}
for s, val in readings
]
}
url = SERVER + "/api/insert_data.php"
body = ujson.dumps(payload)
print(f"[HTTP] POST → {url}")
try:
resp = urequests.post(
url,
data=body,
headers={"Content-Type": "application/json"}
)
result = resp.text
resp.close()
print(f"[Server] {result}")
except OSError as e:
print(f"[HTTP] ERROR: {e}")
print(" Check SERVER and network connection")
def main():
print("\n══════════════════════════════════")
print(" Pico W Multi-Sensor Monitor")
print(f" Sensors : {len(SENSORS)}")
print(f" Interval : {SEND_INTERVAL}s")
print("══════════════════════════════════\n")
wlan = connect_wifi()
cycle = 0
while True:
if not wlan.isconnected():
print("[WiFi] Connection lost — reconnecting...")
wlan = connect_wifi()
cycle += 1
print(f"\n─── Cycle #{cycle} ───────────────────────")
send_all_sensors()
utime.sleep(SEND_INTERVAL)
main()
# ════════════════════════════════════════════════════════════════
# SENSOR SNIPPETS — copy what you need into Step 1
# ════════════════════════════════════════════════════════════════
#
# ── Onboard temperature (Pico W only) ──────────────────────────
# from machine import ADC
# _adc = ADC(4)
# def read_temperature():
# v = _adc.read_u16() * 3.3 / 65535
# return round(27 - (v - 0.706) / 0.001721, 1)
#
# ── DHT11 / DHT22 ───────────────────────────────────────────────
# import dht
# from machine import Pin
# _dht = dht.DHT11(Pin(15)) # or DHT22
# def read_temperature():
# _dht.measure(); return _dht.temperature()
# def read_humidity():
# _dht.measure(); return _dht.humidity()
#
# ── HC-SR04 Ultrasonic ──────────────────────────────────────────
# from machine import Pin, time_pulse_us
# _trig = Pin(14, Pin.OUT)
# _echo = Pin(15, Pin.IN)
# def read_distance():
# _trig.low(); utime.sleep_us(2)
# _trig.high(); utime.sleep_us(10); _trig.low()
# dur = time_pulse_us(_echo, 1, 30000)
# return round(dur / 58.0, 1) if dur > 0 else 0
#
# ── MQ-2 Gas sensor (ADC) ───────────────────────────────────────
# from machine import ADC
# _adc = ADC(26) # GP26 = ADC0
# def read_gas():
# return round(_adc.read_u16() / 65535 * 100, 1)
#
# ── LDR Light sensor ────────────────────────────────────────────
# from machine import ADC
# _ldr = ADC(27) # GP27 = ADC1
# def read_light():
# return round(_ldr.read_u16() / 65535 * 100, 1)
#
# ════════════════════════════════════════════════════════════════
# FOR FULL RASPBERRY PI (Raspbian / Linux)
# Replace the entire file with this simpler version:
#
# pip3 install requests
#
# import requests, time
#
# SERVER = "https://iot.getyourprojectdone.in"
# API_KEY = ""
#
# SENSORS = [
# { "device": "temp_sensor", "type": "temperature", "unit": "C", "fn": lambda: 28.5 },
# { "device": "hum_sensor", "type": "humidity", "unit": "%", "fn": lambda: 60.0 },
# ]
#
# while True:
# payload = {
# "api_key": API_KEY,
# "devices": [
# {"device_name": s["device"],
# "sensors": [{"type": s["type"], "value": str(s["fn"]()), "unit": s["unit"]}]}
# for s in SENSORS
# ]
# }
# r = requests.post(SERVER + "/api/insert_data.php", json=payload)
# print(r.json())
# time.sleep(10)
# ════════════════════════════════════════════════════════════════
raspberry_control.py
"""
════════════════════════════════════════════════════════════════
Raspberry Pi Pico W — Multi-Device Control (MicroPython)
Production-ready • Add unlimited control devices in 2 steps
════════════════════════════════════════════════════════════════
HOW IT WORKS:
Every POLL_INTERVAL seconds → fetches pending commands
Calls the matching handler function for each command
Acknowledges each command back to the server
HOW TO ADD A NEW CONTROL DEVICE:
Step 1 — Write a handler function for the device
Step 2 — Add one dict to DEVICES list below
Command types from dashboard:
"ON" → switch on (relay, LED, buzzer …)
"OFF" → switch off
"SET_VALUE" → set to a level (fan speed %, servo angle …)
════════════════════════════════════════════════════════════════
"""
import network
import urequests
import ujson
import utime
from machine import Pin, PWM
# ── STEP 0 — Credentials & server ────────────────────────────────
WIFI_SSID = "Your-SSID"
WIFI_PASSWORD = "Your-Password"
API_KEY = ""
SERVER = "https://iot.getyourprojectdone.in"
# Local LAMPP: SERVER = "http://192.168.x.x/iot_platform"
POLL_INTERVAL = 5 # seconds
# ─────────────────────────────────────────────────────────────────
# ════════════════════════════════════════════════════════════════
# STEP 1 — Define pins and write one handler per device
#
# Handler signature: def handle_xxx(cmd_type, cmd_value):
# cmd_type : "ON" | "OFF" | "SET_VALUE"
# cmd_value : string, e.g. "75" for SET_VALUE
# ════════════════════════════════════════════════════════════════
# ── Onboard LED (GP25 on Pico W) ─────────────────────────────────
_led = Pin("LED", Pin.OUT) # built-in LED on Pico W
def handle_led(cmd_type, cmd_value):
if cmd_type == "ON":
_led.on()
print("[LED] ON")
elif cmd_type == "OFF":
_led.off()
print("[LED] OFF")
# ── External Relay (active HIGH — wire to any GP pin) ─────────────
_relay = Pin(15, Pin.OUT, value=0) # GP15
def handle_relay(cmd_type, cmd_value):
if cmd_type == "ON":
_relay.on()
print("[Relay] ON")
elif cmd_type == "OFF":
_relay.off()
print("[Relay] OFF")
# ── Fan via PWM (SET_VALUE = 0-100 percent) ───────────────────────
_fan_pwm = PWM(Pin(14)) # GP14
_fan_pwm.freq(1000)
def handle_fan(cmd_type, cmd_value):
if cmd_type == "ON":
_fan_pwm.duty_u16(65535)
print("[Fan] FULL ON")
elif cmd_type == "OFF":
_fan_pwm.duty_u16(0)
print("[Fan] OFF")
elif cmd_type == "SET_VALUE":
pct = max(0, min(100, int(cmd_value)))
duty = int(pct / 100 * 65535)
_fan_pwm.duty_u16(duty)
print(f"[Fan] Speed = {pct}%")
# ── Servo (SET_VALUE = angle 0-180) ──────────────────────────────
# _servo_pwm = PWM(Pin(13)) # GP13
# _servo_pwm.freq(50) # 50 Hz for servo
# def _angle_to_duty(deg):
# # 0.5ms=0° → 2.5ms=180° at 50Hz (period=20ms)
# us = 500 + int(deg / 180 * 2000)
# return int(us / 20000 * 65535)
# def handle_servo(cmd_type, cmd_value):
# if cmd_type == "SET_VALUE":
# angle = max(0, min(180, int(cmd_value)))
# _servo_pwm.duty_u16(_angle_to_duty(angle))
# print(f"[Servo] Angle = {angle}°")
# elif cmd_type == "ON": _servo_pwm.duty_u16(_angle_to_duty(180))
# elif cmd_type == "OFF": _servo_pwm.duty_u16(_angle_to_duty(0))
# ── Buzzer ────────────────────────────────────────────────────────
# _buzzer = Pin(12, Pin.OUT, value=0)
# def handle_buzzer(cmd_type, cmd_value):
# if cmd_type == "ON": _buzzer.on()
# elif cmd_type == "OFF": _buzzer.off()
# elif cmd_type == "SET_VALUE":
# _buzzer.on(); utime.sleep_ms(int(cmd_value)); _buzzer.off()
# ════════════════════════════════════════════════════════════════
# STEP 2 — Register devices in this list
# "device" must EXACTLY match name on your Devices page
# (Device Type must be a control type: relay, led, fan, servo…)
# ════════════════════════════════════════════════════════════════
DEVICES = [
# { "device": "device_name", "handler": handle_function },
{ "device": "led", "handler": handle_led },
{ "device": "relay", "handler": handle_relay },
{ "device": "fan", "handler": handle_fan },
# Uncomment to add:
# { "device": "servo", "handler": handle_servo },
# { "device": "buzzer", "handler": handle_buzzer },
]
# ─────────────────────────────────────────────────────────────────
# Internals — no changes needed below this line
# ─────────────────────────────────────────────────────────────────
def connect_wifi():
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
if wlan.isconnected():
return wlan
print(f"[WiFi] Connecting to {WIFI_SSID}", end="")
wlan.connect(WIFI_SSID, WIFI_PASSWORD)
for _ in range(30):
if wlan.isconnected():
break
utime.sleep(1); print(".", end="")
if wlan.isconnected():
print(f" connected!\n[WiFi] IP: {wlan.ifconfig()[0]}")
else:
print("\n[WiFi] FAILED")
return wlan
def http_post(url, body):
try:
resp = urequests.post(
url,
data=body,
headers={"Content-Type": "application/json"}
)
text = resp.text
resp.close()
return text
except OSError as e:
print(f"[HTTP] Error: {e}")
return ""
def poll_device(device_name, handler):
payload = ujson.dumps({"api_key": API_KEY, "device_name": device_name})
url = SERVER + "/api/device_poll.php"
resp = http_post(url, payload)
if not resp:
return
try:
data = ujson.loads(resp)
except Exception:
print(f"[Poll] Parse error: {resp}")
return
if data.get("status") != "success":
print(f"[Poll] {device_name} — {data.get('message', 'error')}")
return
commands = data.get("commands", [])
if not commands:
return
print(f"[Poll] {device_name} — {len(commands)} command(s)")
for cmd in commands:
cmd_id = cmd.get("id", 0)
c_type = cmd.get("command_type", "")
c_value = cmd.get("command_value", "")
print(f"[CMD] #{cmd_id} {device_name} → type={c_type} value={c_value}")
try:
handler(c_type, c_value)
ack_status = "executed"
except Exception as e:
print(f"[CMD] Handler error: {e}")
ack_status = "failed"
ack_command(cmd_id, ack_status)
utime.sleep_ms(100)
def ack_command(cmd_id, status):
payload = ujson.dumps({
"api_key": API_KEY,
"command_id": cmd_id,
"status": status
})
resp = http_post(SERVER + "/api/device_ack.php", payload)
print(f"[Ack] #{cmd_id} → {resp if resp else 'no response'}")
def main():
print("\n══════════════════════════════════")
print(" Pico W Multi-Device Control")
print(f" Devices : {len(DEVICES)}")
print(f" Interval : {POLL_INTERVAL}s")
print("══════════════════════════════════\n")
wlan = connect_wifi()
cycle = 0
while True:
if not wlan.isconnected():
print("[WiFi] Reconnecting...")
wlan = connect_wifi()
cycle += 1
print(f"\n─── Poll cycle #{cycle} ───")
for dev in DEVICES:
poll_device(dev["device"], dev["handler"])
utime.sleep(POLL_INTERVAL)
main()
Copy any section into your .ino monitor file as Step 1.
Each section includes the library
#include, pin define, and
the read function — ready to drop into SENSORS[].
sensor_library.h — accessory snippets
/*
* ════════════════════════════════════════════════════════════════
* sensor_library.h — Sensor Accessory Code
* Copy-paste any section you need into esp8266_monitor.ino
* or ardiuno_monitor.ino as your Step 1 read functions.
* ════════════════════════════════════════════════════════════════
*
* USAGE:
* 1. Install the required library for your sensor
* 2. Copy the ENTIRE section (includes + pin define + function)
* into your .ino file above the SENSORS[] table
* 3. Use the read function in the SENSORS[] table
*
* AVAILABLE SENSORS:
* • DHT11 / DHT22 — Temperature + Humidity
* • BMP280 — Temperature + Pressure
* • DS18B20 — Temperature (waterproof)
* • HC-SR04 — Ultrasonic Distance
* • MQ-2 / MQ-135 — Gas / Air Quality (analog)
* • LDR — Light level (analog)
* • Soil Moisture — Analog moisture sensor
* • ACS712 — Current sensor (analog)
* • PIR — Motion detection (digital)
* • Water Level — Analog water level
* ════════════════════════════════════════════════════════════════
*/
#pragma once
// ════════════════════════════════════════════════════════════════
// DHT11 / DHT22 — Temperature & Humidity
// Library: "DHT sensor library" by Adafruit (Library Manager)
// Also install: "Adafruit Unified Sensor"
// ════════════════════════════════════════════════════════════════
/*
#include <DHT.h>
#define DHT_PIN D5 // change to your data pin
#define DHT_TYPE DHT11 // DHT11 or DHT22
DHT dht(DHT_PIN, DHT_TYPE);
void initDHT() { dht.begin(); }
float readDHT_Temp() {
float t = dht.readTemperature();
return isnan(t) ? -1 : t;
}
float readDHT_Humidity() {
float h = dht.readHumidity();
return isnan(h) ? -1 : h;
}
// Add to SENSORS[]:
// { "temp_sensor", "temperature", "C", readDHT_Temp },
// { "humidity_sensor", "humidity", "%", readDHT_Humidity },
// Add to setup():
// initDHT();
*/
// ════════════════════════════════════════════════════════════════
// BMP280 — Temperature & Barometric Pressure
// Library: "Adafruit BMP280 Library" (Library Manager)
// Wiring: SDA → D2 (GPIO4), SCL → D1 (GPIO5) [I2C]
// ════════════════════════════════════════════════════════════════
/*
#include <Wire.h>
#include <Adafruit_BMP280.h>
Adafruit_BMP280 bmp;
void initBMP() {
if (!bmp.begin(0x76)) { // try 0x77 if 0x76 fails
Serial.println("[BMP280] Not found — check wiring");
}
}
float readBMP_Temp() { return bmp.readTemperature(); } // °C
float readBMP_Pressure() { return bmp.readPressure() / 100.0; } // hPa
// Add to SENSORS[]:
// { "temp_sensor", "temperature", "C", readBMP_Temp },
// { "pressure_sensor", "pressure", "hPa", readBMP_Pressure },
// Add to setup():
// Wire.begin(); initBMP();
*/
// ════════════════════════════════════════════════════════════════
// DS18B20 — Waterproof Temperature Sensor (1-Wire)
// Library: "DallasTemperature" + "OneWire" (Library Manager)
// Wiring: Data → any digital pin, 4.7 kΩ pullup to 3.3 V
// ════════════════════════════════════════════════════════════════
/*
#include <OneWire.h>
#include <DallasTemperature.h>
#define DS18B20_PIN D4
OneWire oneWire(DS18B20_PIN);
DallasTemperature ds18b20(&oneWire);
void initDS18B20() { ds18b20.begin(); }
float readDS18B20() {
ds18b20.requestTemperatures();
float t = ds18b20.getTempCByIndex(0);
return (t == DEVICE_DISCONNECTED_C) ? -1 : t;
}
// Add to SENSORS[]:
// { "temp_sensor", "temperature", "C", readDS18B20 },
// Add to setup():
// initDS18B20();
*/
// ════════════════════════════════════════════════════════════════
// HC-SR04 — Ultrasonic Distance Sensor
// No library needed — uses pulseIn()
// Wiring: VCC → 5V, TRIG → D6, ECHO → D7 (use voltage divider!)
// ════════════════════════════════════════════════════════════════
/*
#define ULTRASONIC_TRIG D6 // GPIO12
#define ULTRASONIC_ECHO D7 // GPIO13
void initUltrasonic() {
pinMode(ULTRASONIC_TRIG, OUTPUT);
pinMode(ULTRASONIC_ECHO, INPUT);
}
float readUltrasonic() {
// Send pulse
digitalWrite(ULTRASONIC_TRIG, LOW);
delayMicroseconds(2);
digitalWrite(ULTRASONIC_TRIG, HIGH);
delayMicroseconds(10);
digitalWrite(ULTRASONIC_TRIG, LOW);
// Measure echo (timeout = 30 ms → max ~500 cm)
long duration = pulseIn(ULTRASONIC_ECHO, HIGH, 30000);
if (duration == 0) return -1; // out of range
return duration / 58.0; // convert to cm
}
// Add to SENSORS[]:
// { "distance_sensor", "distance", "cm", readUltrasonic },
// Add to setup():
// initUltrasonic();
*/
// ════════════════════════════════════════════════════════════════
// MQ-2 / MQ-135 — Gas / Air Quality Sensor (Analog)
// No library needed — uses analogRead()
// Wiring: AO → A0 (ESP8266 only has one ADC pin)
// Note: ESP8266 ADC is 0-1V (use voltage divider if needed)
// ════════════════════════════════════════════════════════════════
/*
#define GAS_PIN A0
float readGas() {
int raw = analogRead(GAS_PIN); // 0–1023
return raw * (100.0 / 1023.0); // 0–100% scale
// For actual ppm, use sensor datasheet calibration curve
}
// Add to SENSORS[]:
// { "gas_sensor", "gas", "%", readGas },
*/
// ════════════════════════════════════════════════════════════════
// LDR — Light Dependent Resistor (Analog)
// Wiring: LDR + 10 kΩ resistor voltage divider → A0
// ════════════════════════════════════════════════════════════════
/*
#define LDR_PIN A0
float readLDR() {
int raw = analogRead(LDR_PIN); // 0 = dark, 1023 = bright
return raw * (100.0 / 1023.0); // 0–100 lux scale (approximate)
}
// Add to SENSORS[]:
// { "light_sensor", "light", "lux", readLDR },
*/
// ════════════════════════════════════════════════════════════════
// Soil Moisture Sensor (Analog)
// Wiring: AO → A0
// Output: 0% = dry, 100% = wet (inverted — raw 1023=dry, 0=wet)
// ════════════════════════════════════════════════════════════════
/*
#define SOIL_PIN A0
float readSoilMoisture() {
int raw = analogRead(SOIL_PIN);
return (1023 - raw) * (100.0 / 1023.0); // invert so 100% = wet
}
// Add to SENSORS[]:
// { "soil_sensor", "moisture", "%", readSoilMoisture },
*/
// ════════════════════════════════════════════════════════════════
// ACS712 — Current Sensor (5A / 20A / 30A variants) (Analog)
// Wiring: OUT → A0
// ════════════════════════════════════════════════════════════════
/*
#define ACS712_PIN A0
#define ACS712_SENSITIVITY 0.185 // V/A for 5A module (use 0.100 for 20A, 0.066 for 30A)
#define ACS712_VREF 2.5 // V (midpoint at VCC/2)
float readCurrent() {
int raw = analogRead(ACS712_PIN);
float voltage = raw * (3.3 / 1023.0); // ADC voltage
float current = (voltage - ACS712_VREF) / ACS712_SENSITIVITY;
return abs(current);
}
// Add to SENSORS[]:
// { "current_sensor", "current", "A", readCurrent },
*/
// ════════════════════════════════════════════════════════════════
// PIR — Motion Detection Sensor (Digital)
// Wiring: OUT → D5 (any digital pin)
// Returns 1.0 = motion detected, 0.0 = no motion
// ════════════════════════════════════════════════════════════════
/*
#define PIR_PIN D5
void initPIR() { pinMode(PIR_PIN, INPUT); }
float readPIR() {
return digitalRead(PIR_PIN) ? 1.0 : 0.0;
}
// Add to SENSORS[]:
// { "pir_sensor", "motion", "", readPIR },
// Add to setup():
// initPIR();
*/
// ════════════════════════════════════════════════════════════════
// Water Level Sensor (Analog)
// Wiring: S (signal) → A0
// ════════════════════════════════════════════════════════════════
/*
#define WATER_PIN A0
float readWaterLevel() {
int raw = analogRead(WATER_PIN);
return raw * (100.0 / 1023.0); // 0–100%
}
// Add to SENSORS[]:
// { "water_sensor", "water_level", "%", readWaterLevel },
*/
API Reference
| Endpoint | Method | Purpose | Required JSON Fields | Response |
|---|---|---|---|---|
/api/insert_data.php |
POST | Send sensor readings from device to platform | api_key, devices[] → device_name, sensors[] → type, value, unit |
{"status":"success"} |
/api/device_poll.php |
POST | Fetch pending commands for a control device | api_key, device_name |
{"status":"success","commands":[{id, command_type, command_value}]} |
/api/device_ack.php |
POST | Acknowledge a command was executed | api_key, command_id, status ("executed"|"failed") |
{"status":"success","message":"Command #N marked as executed"} |
/api/fetch_data.php |
POST | Read stored sensor data (used by charts) | api_key + optional ?limit=N |
JSON array of sensor readings |
Supported Sensor Types
Use these exact strings as the type
field in your sensor definition. The chart will color-code automatically.
temperaturehumiditygasdistancepressurelightphco2motioncurrentvoltagemoisturewater_levelspeedweightflowsoundvibrationstatuscustom
Control Device Types
| Device Type | Dashboard Widget | Commands Sent |
|---|---|---|
relay / switch / led | Toggle switch | ON / OFF |
fan / dimmer | Slider (0–100) | SET_VALUE with 0–100 |
servo | Slider (0–180) | SET_VALUE with 0–180 |
motor | Slider (0–100) | SET_VALUE with 0–100 |
rgb | Color picker | SET_VALUE with hex color |
buzzer | Toggle switch | ON / OFF |
lock / valve | Toggle switch | ON / OFF |