#include <ESP8266WiFi.h>
#include <SoftwareSerial.h>
#include <Adafruit_MQTT_Client.h>
#include <ArduinoJson.h>
#define AIO_SERVER "io.adafruit.com"
#define AIO_SERVERPORT 1883
#define AIO_USERNAME "YOUR_AIO_USERNAME"
#define AIO_KEY "YOUR_AIO_KEY"
const char* ssid = "YOUR_SSID";
const char* password = "SSID_PASSWORD";
SoftwareSerial softSerial(D2, D3); // RX, TX
const int RELAY_PIN[] = {14, 12};
WiFiClient client;
Adafruit_MQTT_Client mqtt(&client, AIO_SERVER, AIO_SERVERPORT, AIO_USERNAME, AIO_USERNAME, AIO_KEY);
Adafruit_MQTT_Publish temp(&mqtt, AIO_USERNAME "/feeds/irrigation.temperature");
Adafruit_MQTT_Publish humi(&mqtt, AIO_USERNAME "/feeds/irrigation.humidity");
Adafruit_MQTT_Publish soil(&mqtt, AIO_USERNAME "/feeds/irrigation.soilMoisture");
Adafruit_MQTT_Publish rain(&mqtt, AIO_USERNAME "/feeds/irrigation.rainSensor");
Adafruit_MQTT_Subscribe bt1 = Adafruit_MQTT_Subscribe(&mqtt, AIO_USERNAME "/feeds/irrigation.relay1");
Adafruit_MQTT_Subscribe bt2 = Adafruit_MQTT_Subscribe(&mqtt, AIO_USERNAME "/feeds/irrigation.relay2");
bool mqttConnected = false;
void setup() {
Serial.begin(115200);
softSerial.begin(9600);
connectToWiFi();
connectToMQTT();
for (int i = 0; i < 2; i++) {
pinMode(RELAY_PIN[i], OUTPUT);
}
}
void loop() {
if (WiFi.status() != WL_CONNECTED) {
connectToWiFi();
connectToMQTT();
}
if (mqttConnected) {
mqtt.processPackets(200);
mqtt.ping();
onRelayChange();
}
if (softSerial.available()) {
String jsonStr = softSerial.readStringUntil('\n');
deserializeAndPublish(jsonStr);
Serial.println(jsonStr);
}
}
void connectToWiFi() {
WiFi.begin(ssid, password);
Serial.print("Connecting to WiFi...");
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
}
Serial.println("Connected to WiFi");
}
void connectToMQTT() {
int8_t ret;
uint32_t connectDelay = 5000;
Serial.print("Connecting to MQTT... ");
while ((ret = mqtt.connect()) != 0) {
Serial.println(mqtt.connectErrorString(ret));
Serial.println("Retrying MQTT connection in 5 seconds...");
delay(connectDelay);
connectDelay += 5000; // Increment the delay for each retry
}
mqttConnected = true;
Serial.println("MQTT connected!");
}
void deserializeAndPublish(const String& jsonStr) {
DynamicJsonDocument jsonDoc(256);
DeserializationError error = deserializeJson(jsonDoc, jsonStr);
if (error) {
Serial.print("deserializeJson() failed: ");
Serial.println(error.c_str());
return;
}
float temperature = jsonDoc["temperature"].as<float>();
float humidity = jsonDoc["humidity"].as<float>();
float soilMoisture = jsonDoc["soil_moisture"].as<float>();
float rainSensor = jsonDoc["rain_sensor"].as<float>();
publishValue(temp, temperature);
publishValue(humi, humidity);
publishValue(soil, soilMoisture);
publishValue(rain, rainSensor);
printSensorData("Temp", temperature);
printSensorData("Humi", humidity);
printSensorData("Soil", soilMoisture);
printSensorData("Rain", rainSensor);
}
void onRelayChange() {
Adafruit_MQTT_Subscribe *subscription;
while ((subscription = mqtt.readSubscription(5000))) {
if (subscription == &bt1) {
Serial.print(F("Got r1 : "));
Serial.println((char *)bt1.lastread);
int bt1_State = atoi((char *)bt1.lastread);
relaySwitch(0, bt1_State);
}
if (subscription == &bt2) {
Serial.print(F("Got r2 : "));
Serial.println((char *)bt2.lastread);
int bt2_State = atoi((char *)bt2.lastread);
relaySwitch(1, bt2_State);
}
}
}
void relaySwitch(int index, int pinValue) {
digitalWrite(RELAY_PIN[index], pinValue);
}
void publishValue(Adafruit_MQTT_Publish &feed, float value) {
if (!feed.publish(value)) {
Serial.println("Failed to publish data to MQTT topic");
}
}
void printSensorData(const char* sensorName, float value) {
Serial.print(sensorName);
Serial.print(": ");
Serial.println(value);
}