Skip to content

Commit

Permalink
Merge pull request absalom-muc#145 from glsf91/master
Browse files Browse the repository at this point in the history
Changed WiFi connection setup and continue when MQTT failed
  • Loading branch information
glsf91 authored Apr 24, 2023
2 parents e9bccf4 + fde73eb commit c646c50
Show file tree
Hide file tree
Showing 6 changed files with 99 additions and 42 deletions.
5 changes: 3 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,9 @@ I assume that all AC units of the type "SRK xx ZS-S" / "SRC xx ZS-S" are support

Unsupported models:

– SRK xx ZSPR-S

- SRK xx ZSPR-S
- SRK71ZEA-S1

If you find out that also other models are supported that are not listed here, please give feedback so that I can expand the list.

# Installing:
Expand Down
16 changes: 16 additions & 0 deletions SW-Configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,7 @@ RSSI |r |integer |WiFI RSSI / signal Strength in dBm after MQTT (re
Version |r |string |Version number of MHI-AC-Ctrl
WIFI_LOST|r |integer |number of lost WiFi connections since last reset
MQTT_LOST|r |integer |number of lost MQTT connections since last reset
APs |r |string |Matched APs seen at scan with RSSI value

note: The topic and the payload text of the status data is adaptable by defines in [MHI-AC-Ctrl.h](src/MHI-AC-Ctrl.h)

Expand Down Expand Up @@ -246,6 +247,20 @@ With the following parameter you can change this minimum interval of 5 seconds.

This jitter can also be avoided by using the TROOM_FILTER_LIMIT as descibed above. But this filter is also used if the temperature is provided by an external temperature sensor or a connected DS18B20. With above it will be also possible to see smaller changes.

## Not switching off AC when MQTT connections fails ([MHI-AC-Ctrl.h](src/MHI-AC-Ctrl.h))
Default the module stops communicating with the AC when the MQTT connection get disconnected. After 120 sec the AC will power off because of [this](https://github.com/absalom-muc/MHI-AC-Ctrl/blob/master/Troubleshooting.md#fire-ac-switches-power-off-sometimes).
When using a DS18x20 as room temperature sensor, this can be unwanted behaviour. Also at night or when not at home when this happens, can be unwanted behaviour.
This behaviour can be changed by changing the following line:
```
//#define CONTINUE_WITHOUT_MQTT true
```
to
```
#define CONTINUE_WITHOUT_MQTT true
```

Warning: be aware that there might be some safety implication and that the deactivation of this feature is on your own risk.
The AC now keeps running and no control is possible anymore when MQTT is disconnected. Also of course no MQTT topics are updated anymore. Of course control is still possible with the remote control.

## MHI-AC-Ctrl partitioning
MHI-AC-Ctrl-core implements the core functions (SPI read/write, communication with the wrapper).
Expand Down Expand Up @@ -325,3 +340,4 @@ You find here some examples for integration of MHI-AC-Ctrl
- [ioBroker](https://forum.iobroker.net/topic/17041/anfrage-airconwithme-intesishome-klimasteuerung-adapter/14)
- [FHEM](https://forum.fhem.de/index.php/topic,88841.0/all.html)
- [WiFi SSID, hostname and MQTT server dynamic](https://github.com/absalom-muc/MHI-AC-Ctrl/pull/69)
- [Web page with MQTT](https://github.com/absalom-muc/MHI-AC-Ctrl/issues/141)
8 changes: 7 additions & 1 deletion Version.md
Original file line number Diff line number Diff line change
@@ -1,13 +1,19 @@
MHI-AC-Ctrl by absalom-muc

**v2.7R4** (April 2023)
- changed setup WiFi connection to async; module starts already communicating with AC during WiFi setup and also during scanning when WiFI_SEARCHStrongestAP is used by [glsf91](https://github.com/glsf91)
- added CONTINUE_WITHOUT_MQTT; module keeps communicating with AC if MQTT is disconnected. See also description in SW-Configuration.md and [Question: why mhi_ac_ctrl_core.loop only when MQTT connected? #144](https://github.com/absalom-muc/MHI-AC-Ctrl/issues/144) by [glsf91](https://github.com/glsf91)
- fix bug for publish list of access points by [glsf91](https://github.com/glsf91)
- added SRK71ZEA-S1 to unsupported list [Addition to unsupported list #143](https://github.com/absalom-muc/MHI-AC-Ctrl/issues/143) by [glsf91](https://github.com/glsf91)
- added Web page [Webpage for accessing MQTT data #141](https://github.com/absalom-muc/MHI-AC-Ctrl/issues/141) to integration list by [glsf91](https://github.com/glsf91)

**v2.7R3** (March 2023)
- fix some compiler warnings by [glsf91](https://github.com/glsf91)
- change sending MISO with faster refresh of data every 20s by [glsf91](https://github.com/glsf91)
- avoid jitter with internal temperature sensor, now updating atmost every 5s by [glsf91](https://github.com/glsf91)
- fix print wifi encryption type by [glsf91](https://github.com/glsf91)
- skip not usable values for DB18B20 by [glsf91](https://github.com/glsf91)


**v2.7R2** (March 2023)
- Added energy kWh from airco by [glsf91](https://github.com/glsf91).

Expand Down
17 changes: 12 additions & 5 deletions src/MHI-AC-Ctrl.ino
Original file line number Diff line number Diff line change
Expand Up @@ -414,10 +414,13 @@ void setup() {

void loop() {
static byte ds18x20_value_old = 0;
static int WiFiStatus = WIFI_CONNECT_TIMEOUT;
static int WiFiStatus = WIFI_CONNECT_TIMEOUT; // start connecting to WiFi
static int MQTTStatus = MQTT_NOT_CONNECTED;
static unsigned long previousMillis = millis();
if (((WiFi.status() != WL_CONNECTED) | (WiFiStatus != WIFI_CONNECT_OK)) || (WiFI_SEARCHStrongestAP & (millis() - previousMillis >= WiFI_SEARCH_FOR_STRONGER_AP_INTERVALL*60*1000))) {

if (((WiFi.status() != WL_CONNECTED) ||
(WiFiStatus != WIFI_CONNECT_OK)) ||
(WiFI_SEARCHStrongestAP && (millis() - previousMillis >= WiFI_SEARCH_FOR_STRONGER_AP_INTERVALL*60*1000))) {
//Serial.printf("loop: call setupWiFi(WiFiStatus)\n");
setupWiFi(WiFiStatus);
previousMillis = millis();
Expand Down Expand Up @@ -449,19 +452,23 @@ void loop() {
}
#endif
#endif

// fallback to AC internal Troom temperature sensor
if(troom_was_set_by_MQTT & (millis() - room_temp_set_timeout_Millis >= ROOM_TEMP_MQTT_SET_TIMEOUT*1000)) {
mhi_ac_ctrl_core.set_troom(0xff); // use IU temperature sensor
Serial.println(F("ROOM_TEMP_MQTT_SET_TIMEOUT exceeded, use IU temperature sensor value!"));
troom_was_set_by_MQTT=false;
}

if((MQTTStatus==MQTT_RECONNECTED)|(MQTTStatus==MQTT_CONNECT_OK)){
#ifndef CONTINUE_WITHOUT_MQTT
if((MQTTStatus==MQTT_RECONNECTED) || (MQTTStatus==MQTT_CONNECT_OK)){
#endif
//Serial.println("MQTT connected in main loop");
int ret = mhi_ac_ctrl_core.loop(80);
if (ret < 0)
Serial.printf_P(PSTR("mhi_ac_ctrl_core.loop error: %i\n"), ret);
#ifndef CONTINUE_WITHOUT_MQTT
}
/*else
Serial.println("MQTT NOT connected in main loop");*/
#endif

}
85 changes: 52 additions & 33 deletions src/support.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,54 +69,73 @@ void initWiFi(){
WiFi.setAutoReconnect(false);
}

int WiFiStatus = WIFI_CONNECT_TIMEOUT;
uint networksFound = 0;
void setupWiFi(int& WiFiStatus) {
unsigned long WiFiTimeoutMillis;

void handleWiFiScanResult(int WifinetworksFound) { // Handles async WiFi scan result
int max_rssi = -999;
int strongest_AP = -1;
static unsigned long WiFiTimeoutMillis;

if(WiFiStatus != WIFI_CONNECT_ONGOING) {
WiFi.scanDelete();
uint networksFound = WiFi.scanNetworks();
Serial.printf("setupWiFi:%i access points available\n", networksFound);
for (uint i = 0; i < networksFound; i++)
{
Serial.printf("%2d %25s %2d %ddBm %s %s %02x\n", i + 1, WiFi.SSID(i).c_str(), WiFi.channel(i), WiFi.RSSI(i), WiFi.BSSIDstr(i).c_str(), WiFi.encryptionType(i) == ENC_TYPE_NONE ? "open" : "secured", (uint)WiFi.encryptionType(i));
if((strcmp(WiFi.SSID(i).c_str(), WIFI_SSID) == 0) && (WiFi.RSSI(i)>max_rssi)){
max_rssi = WiFi.RSSI(i);
strongest_AP = i;
}
networksFound = WifinetworksFound; // will be used other places

Serial.printf_P(PSTR("handleWiFiScanResult(): %i access points available\n"), networksFound);
for (uint i = 0; i < networksFound; i++)
{
Serial.printf("%2d %25s %2d %ddBm %s %s %02x\n", i + 1, WiFi.SSID(i).c_str(), WiFi.channel(i), WiFi.RSSI(i), WiFi.BSSIDstr(i).c_str(), WiFi.encryptionType(i) == ENC_TYPE_NONE ? "open" : "secured", (uint)WiFi.encryptionType(i));
if((strcmp(WiFi.SSID(i).c_str(), WIFI_SSID) == 0) && (WiFi.RSSI(i)>max_rssi)){
max_rssi = WiFi.RSSI(i);
strongest_AP = i;
}
Serial.printf("setupWiFi2:%i access points available\n", networksFound);
Serial.printf_P("current BSSID: %s, strongest BSSID: %s\n", WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str());
if((WiFi.status() != WL_CONNECTED) || ((max_rssi > WiFi.RSSI() + 10) && (strcmp(WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str()) != 0))) {
if(strongest_AP != -1) {
Serial.printf("Connecting from bssid:%s to bssid:%s, channel:%i\n", WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str(), WiFi.channel(strongest_AP));
WiFi.begin(WIFI_SSID, WIFI_PASSWORD, WiFi.channel(strongest_AP), WiFi.BSSID(strongest_AP), true);
}
else {
Serial.println("No matching AP found (maybe hidden SSID), however try to connect.");
WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
}
WiFiStatus = WIFI_CONNECT_ONGOING;
Serial.println("WIFI_CONNECT_ONGOING");
WiFiTimeoutMillis = millis();
}
Serial.printf_P(PSTR("current BSSID: %s, strongest BSSID: %s\n"), WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str());
if((WiFi.status() != WL_CONNECTED) || ((max_rssi > WiFi.RSSI() + 10) && (strcmp(WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str()) != 0))) {
if(strongest_AP != -1) {
Serial.printf_P(PSTR("Connecting from bssid:%s to bssid:%s, channel:%i\n"), WiFi.BSSIDstr().c_str(), WiFi.BSSIDstr(strongest_AP).c_str(), WiFi.channel(strongest_AP));
WiFi.begin(WIFI_SSID, WIFI_PASSWORD, WiFi.channel(strongest_AP), WiFi.BSSID(strongest_AP), true);
}
else {
Serial.println(F("No matching AP found (maybe hidden SSID), however try to connect."));
WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
}
WiFiStatus = WIFI_CONNECT_ONGOING;
Serial.println(F("WIFI_CONNECT_ONGOING"));
WiFiTimeoutMillis = millis();
}
else { // scanning is started for WiFI_SEARCHStrongestAP and WiFi was already connected
WiFiStatus = WIFI_CONNECT_SCANNING_DONE;
Serial.println(F("WIFI_CONNECT_SCANNING_DONE"));
}
}

void setupWiFi(int& WiFiStatusParam) {

if(WiFiStatus != WIFI_CONNECT_ONGOING) { // WIFI_CONNECT_OK or WIFI_CONNECT_TIMEOUT or WIFI_CONNECT_SCANNING or WIFI_CONNECT_SCANNING_DONE
if (WiFiStatus == WIFI_CONNECT_OK || WiFiStatus == WIFI_CONNECT_TIMEOUT){ // Start scanning async if not in already in progress
WiFi.scanDelete();
Serial.println(F("setupWiFi: Start async scanNetworks"));
WiFi.scanNetworksAsync(handleWiFiScanResult);
WiFiStatus = WIFI_CONNECT_SCANNING;
Serial.println(F("WIFI_CONNECT_SCANNING"));
}

if (WiFiStatus == WIFI_CONNECT_SCANNING_DONE){ // after scanning for WiFI_SEARCHStrongestAP. Should be still connected
WiFiStatus = WIFI_CONNECT_OK;
Serial.println(F("WIFI_CONNECT_OK"));
}
//Serial.printf("setupWiFi3:%i access points available\n", networksFound);
}
else { // WiFiStatus == WIFI_CONNECT_ONGOING
if(WiFi.status() == WL_CONNECTED){
Serial.printf_P(PSTR(" connected to %s, IP address: %s (%ddBm)\n"), WIFI_SSID, WiFi.localIP().toString().c_str(), WiFi.RSSI());
WiFiStatus = WIFI_CONNECT_OK;
Serial.println("WIFI_CONNECT_OK");
Serial.println(F("WIFI_CONNECT_OK"));
}
else if(millis() - WiFiTimeoutMillis > 10*1000) { // timeout after 10 seconds
WiFiStatus = WIFI_CONNECT_TIMEOUT;
Serial.println(PSTR("WIFI_CONNECT_TIMEOUT"));
Serial.println(F("WIFI_CONNECT_TIMEOUT"));
}
//Serial.printf("setupWiFi4:%i access points available\n", networksFound);
}
//Serial.printf("setupWiFi E:%i access points available\n", networksFound);
WiFiStatusParam = WiFiStatus; // return WiFiStatus to caller
}

int MQTTreconnect() {
Expand Down Expand Up @@ -147,7 +166,7 @@ int MQTTreconnect() {
output_P((ACStatus)type_status, PSTR(TOPIC_WIFI_BSSID), strtmp);

// for testing publish list of access points with the expected SSID
Serial.printf("%i access points available\n", networksFound); // unlar, warum hier networksFound=0 !!!
Serial.printf("MQTTreconnect(): %i access points available\n", networksFound);
for (uint i = 0; i < networksFound; i++)
{
if(strcmp(WiFi.SSID(i).c_str(), WIFI_SSID) == 0){
Expand Down
10 changes: 9 additions & 1 deletion src/support.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include "MHI-AC-Ctrl-core.h"
#include "MHI-AC-Ctrl.h"

#define VERSION "2.7R3"
#define VERSION "2.7R4"

#define WIFI_SSID ""
#define WIFI_PASSWORD ""
Expand Down Expand Up @@ -45,6 +45,12 @@
//#define ENHANCED_RESOLUTION true // when using Tsetpoint with x.5 degrees, airco will use (x+1).0 setpoint
// uncomment this to compensatie (offset) Troom for this.
// this will simulate .x degrees resolution
//#define CONTINUE_WITHOUT_MQTT true // uncomment if communication with AC has to continue when MQTT or WiFi connection is disconnected.
// When Troom is supplied from external, it will fallback to AC internal Troom temperature sensor
// When ROOM_TEMP_DS18X20 is used, it will use room temperature from DS18x20



// *** The configuration ends here ***

#include <ESP8266WiFi.h> // https://github.com/esp8266/Arduino/tree/master/libraries/ESP8266WiFi
Expand Down Expand Up @@ -77,6 +83,8 @@ void setupOTA(); // initialize and
void setup_ds18x20(); // setup the temperature measurement
byte getDs18x20Temperature(int temp_hysterese); // read the temperature from the DS18x20 sensor

#define WIFI_CONNECT_SCANNING 4
#define WIFI_CONNECT_SCANNING_DONE 3
#define WIFI_CONNECT_TIMEOUT 2
#define WIFI_CONNECT_ONGOING 1
#define WIFI_CONNECT_OK 0
Expand Down

0 comments on commit c646c50

Please sign in to comment.