#include #include #include #include #include #include #define has_ntp #if defined has_ntp #define ntptimeoffset 7200 // 2 h in sec #include #include WiFiUDP ntpUDP; NTPClient timeClient(ntpUDP); #endif ESP8266WebServer server(80); ESP8266HTTPUpdateServer httpUpdater; const char *ssid = "FSM"; const char *password = "0101010101"; String Shelly_IP = "192.168.178.47"; String WP_IP = "192.168.178.66"; int8_t WPstate = 0; // positive = on #define WPcmdwait 10 // 10 min int WPtimer = 3; int16_t HIlimit = 100; int16_t LOlimit = -500; boolean IsActive = true; #define historylen 20 // in min #define timeinterval 60000 // 1 minute in ms const int LED = LED_BUILTIN; void setup() { //WiFi.setSleepMode(WIFI_NONE_SLEEP); pinMode(LED, OUTPUT); digitalWrite(LED, LOW); Serial.begin(115200); Serial.println("Start"); Serial.flush(); delay(500); WiFi.mode(WIFI_STA); WiFi.begin(ssid, password); while (WiFi.status() != WL_CONNECTED) { delay(500); Serial.print("."); } Serial.println(" connected to WiFi"); Serial.println(WiFi.localIP()); httpUpdater.setup(&server,"/up"); server.on("/", getGraph); server.on("/pwr.svg", drawGraph); server.on("/cmd", handleCmd); server.onNotFound(handleNotFound); server.begin(); Serial.println("HTTP server started"); #if defined has_ntp timeClient.begin(); timeClient.setTimeOffset(ntptimeoffset); // in sec timeClient.setUpdateInterval(43200000UL); // in ms 12h timeClient.update(); if (timeClient.isTimeSet()) { Serial.print("NTP time"); Serial.println(timeClient.getFormattedTime()); } #endif digitalWrite(LED, HIGH); } int actled; int pwrsum; int pwr1,pwr2,pwr3; int http_get(String getstr) { StaticJsonDocument<200> doc; WiFiClient client; HTTPClient http; int pwr = 12345; if (http.begin(client, getstr)) { int httpCode = http.GET(); if (httpCode > 0) { if (httpCode == HTTP_CODE_OK || httpCode == HTTP_CODE_MOVED_PERMANENTLY) { String payload = http.getString(); //Serial.println(payload); DeserializationError error = deserializeJson(doc, payload); if (error) { Serial.print(F("deserializeJson() failed: ")); Serial.println(error.f_str()); } else pwr = doc["power"]; } } else Serial.printf("[HTTP] GET... failed, error: %s\n", http.errorToString(httpCode).c_str()); http.end(); } else Serial.printf("[HTTP} Unable to connect\n"); return pwr; } void http_WPcontrol(String getstr) { WiFiClient client; HTTPClient http; if (http.begin(client, getstr)) { int httpCode = http.GET(); if (httpCode > 0) Serial.println("WP control OK"); else Serial.println("WP control failed"); http.end(); } } int pwrhistory[historylen] = {0}; uint8_t pwrhistorypt; int totalpwrsum = 0; int totalpwr; unsigned long nextTime; int actMinute; int actHour; void loop() { boolean fail = false; if (WiFi.status() == WL_CONNECTED) { digitalWrite(LED, !digitalRead(LED)); pwr1 = http_get("http://" + Shelly_IP + "/emeter/0"); if (pwr1 == 12345) fail = true; pwr2 = http_get("http://" + Shelly_IP + "/emeter/1"); if (pwr2 == 12345) fail = true; pwr3 = http_get("http://" + Shelly_IP + "/emeter/2"); if (pwr3 == 12345) fail = true; digitalWrite(LED, !digitalRead(LED)); } else fail = true; if (fail) Serial.println("get pwr failed"); else { pwrsum = constrain(pwr1 + pwr2 + pwr3,-1000,1000); pwrhistorypt++; if (pwrhistorypt >= historylen) pwrhistorypt = 0; totalpwrsum -= pwrhistory[pwrhistorypt]; pwrhistory[pwrhistorypt] = pwrsum; totalpwrsum += pwrsum; totalpwr = totalpwrsum/(historylen); Serial.print(pwrsum); Serial.print(" "); Serial.print(totalpwr); Serial.print(" "); if (IsActive) { if (WPtimer == 0) { if (totalpwr >= HIlimit) { if (WPstate > -2) { Serial.print("switch WP off"); Serial.print(" "); digitalWrite(LED, HIGH); http_WPcontrol("http://" + WP_IP + "/cmd?off40"); if (WPstate > 0) WPstate = 0; WPstate--; WPtimer = WPcmdwait; } } else if (totalpwr <= LOlimit) { if (WPstate < 2) { Serial.print("switch WP on"); Serial.print(" "); digitalWrite(LED, LOW); http_WPcontrol("http://" + WP_IP + "/cmd?on60"); if (WPstate < 0) WPstate = 0; WPstate++; WPtimer = WPcmdwait; } } } else WPtimer--; } // is active // 720 points, every min -> 12h. #if defined has_ntp actHour = timeClient.getHours(); storewp(pwrsum, totalpwr, WPstate, actHour); #else storewp(pwrsum, totalpwr, WPstate); #endif } // if not fail Serial.println(); #if defined has_ntp while (timeClient.getMinutes() == actMinute) server.handleClient(); actMinute = timeClient.getMinutes(); #else while (millis() <= nextTime) server.handleClient(); nextTime = timeinterval + millis(); // 60 sec #endif }