#include #include #include #include #include #include "config.h" #include "constants.h" #include "mqtt_discovery.hpp" #include "values.hpp" INCTXT(RootCA, "isrgrootx1.pem"); RTC_DATA_ATTR uint32_t boot_count = 0; WiFiClientSecure sock; PubSubClient mqtt(sock); Values values; Adafruit_seesaw ss; void setup() { Serial.begin(115200); pinMode(13, OUTPUT); digitalWrite(13, 1); // VSCode is slow to open the serial console after upload if (boot_count == 0) { delay(1000); } boot_count++; Serial.printf("This is boot number %d\n", boot_count); if (!wifi_connect()) { Serial.printf("Failed to connect to WiFi, status %s\n", WiFi.status()); retry_after_minutes(1); } if (!mqtt_connect()) { Serial.println("Could not connect to MQTT"); retry_after_minutes(1); } if (!publish_all_config(&mqtt, WiFi.macAddress().c_str())) { Serial.println("Failed to publish device configuration!"); Serial.println(mqtt.state()); } if (!ss.begin(0x36)) { auto msg = "Seesaw not found"; Serial.println(msg); mqtt_send_error(msg); retry_after_minutes(1); } values.boot_count = boot_count; if (!values.read(&ss)) { auto msg = "Failed to get sensor values"; Serial.println(msg); mqtt_send_error(msg); retry_after_minutes(1); } else { Serial.println("Got Values:"); Serial.printf(" Moisture: %d\n", values.moisture); Serial.printf(" Temperature: %.02f\n", values.temperature); Serial.printf(" Battery: %.02f\n", values.battery); Serial.printf(" RSSI: %d\n", values.rssi); Serial.printf(" Boot Count: %d\n", values.boot_count); if (!values.send(&mqtt, TOPIC_STATE)) { Serial.println("Failed to send sensor values"); } } Serial.println("Disconnecting from MQTT broker ..."); mqtt.disconnect(); delay(1000); unsigned long timer = ((boot_count <= 5 ? SLEEP_MILLIS_EARLY : SLEEP_MILLIS) - millis()); Serial.printf("Entering deep sleep for %d milliseconds...\n", timer); Serial.flush(); esp_sleep_enable_timer_wakeup(timer * 1000); esp_deep_sleep_start(); } void loop() { digitalWrite(13, 0); while (1) delay(1471228928); } boolean wifi_connect() { Serial.printf("Connecting to WiFi (%s) ", CFG_WIFI_SSID); WiFi.begin(CFG_WIFI_SSID, CFG_WIFI_PSK); while (WiFi.status() != WL_CONNECTED) { delay(500); if (millis() >= 5000) { break; } Serial.print("."); Serial.flush(); } Serial.println(); if (WiFi.status() != WL_CONNECTED) { return false; } Serial.println("WiFi connected"); Serial.printf(" IP address: %s\n", WiFi.localIP().toString()); Serial.printf(" DNS server: %s\n", WiFi.dnsIP().toString()); Serial.printf(" Default gateway: %s\n", WiFi.gatewayIP().toString()); return true; } boolean mqtt_connect() { sock.setCACert(gRootCAData); int retries = 3; mqtt.setServer(CFG_MQTT_SERVER, CFG_MQTT_PORT); for (;;) { Serial.print("Connecting to MQTT ... "); Serial.flush(); if (!mqtt.connect(CFG_MQTT_CLIENTID, CFG_MQTT_USERNAME, CFG_MQTT_PASSWORD)) { Serial.println(mqtt.state()); mqtt.disconnect(); delay(1000); retries--; if (retries < 1) { return false; } } else { Serial.println("OK"); break; } } if (!mqtt.setBufferSize(512)) { Serial.println("Failed to set MQTT client buffer size!"); return false; } return true; } void mqtt_send_error(const char* msg) { if (!mqtt.connected()) { Serial.println("MQTT client not connected, cannot send error message"); return; } mqtt.publish(TOPIC_ERRORS, msg); } void retry_after_minutes(int minutes) { if (mqtt.connected()) { mqtt.disconnect(); } esp_sleep_enable_timer_wakeup(minutes * 60 * 1000 * 1000); esp_deep_sleep_start(); }