RoganDawes
Expert Member
I wanted to smarten up my geyser, because while I have solar panels and a battery, eventually the battery is full, and the sun is still shining, leaving energy going to waste. I figured that since I also have an electric geyser, I could use excess energy to heat water, which would otherwise need to come from the grid. I had an electrician move my geyser to the AUX port of my Sunsynk 8kW inverter, but was not happy with the fine-grained controllability of this, and also needed to know what the actual temperature of the water in the geyser was, to know when to turn it on and off.
Wanting to keep a physical failsafe, but still monitor the temperature was a problem. Having pondered all sorts of ways of putting a sensor inside the thermostat, but knowing that I also didn't really want to deal with any leaks if anything went wrong, I decided to go with a commercial product. I found the Geyserwise thermostat for sale by itself at an online store (normally only available as part of a much more comprehensive, and expensive, setup). This contains an NTC thermistor, which is an analog device, meant to form part of a voltage divider. Easy enough to work with, one would think!
The geyser has a 3kW element, which at 220V means a 20A relay should do the trick. First I got a CBI Astute Smart Controller, which is rated for 30A, and reprogrammed it using the LibreTuya-ESPHome project, since it is using a RTL8710BN microcontroller. However, my electrician told me that it could not be installed near to the geyser, as it was not an isolator. I then got the CBI Astute Smart Isolator, and did the same reprogramming. I then realised that the CBI Devices were not mains isolated at their GPIO's, and that connecting the external temperature sensor would potentially be routing 220V into the inside of my geyser! Time for a new approach, using something designed to use external sensors!
The best match I could find for this was the Sonoff THR320, which has a 20A relay, and a RJ9 plug for an external sensor. And if you look at the internals, there is an actual transformer stepping down mains voltage, and isolating the ESP32 in the process. Perfect! The downside, which I only figured out later, was that the exposed GPIO on the RJ9 port was connected to GPIO25, which is in the ADC2 group. Which is not usable if WiFi is in use. I considered a few options:
1. reroute GPIO25 to a GPIO in the ADC1 group. Problem: None of them were exposed on pins or pin headers, and the ESP32 is a VERY fine pitch package in amongst a number of other components, I don't trust my soldering enough to put a wire on the right pin!
2. Turn off the WiFi periodically, take the reading, and turn it back on again. Problem: I wasn't sure that this would work, and I didn't want to take chances with it failing in the wrong state.
3. Since the THR320 was designed for use with 1-wire sensors, somehow make the analog NTC thermistor appear to be a 1-wire sensor.
EDIT: 4. Another option that I only thought of later is to replace the thermistor entirely with a DS18B20 1-wire sensor at the end of the brass tube of the thermostat. This might require trimming the brass tube to allow enough space for the slightly larger component, and also needs 3 wires (in theory you can use 2, would probably also require some testing to be sure).
Googling for 1-wire slave implementations, I found a few, but the most promising was https://github.com/orgua/OneWireHub. This claimed to support a variety of microcontrollers, including the ATTiny85. I found a supplier with some ATTiny412's in stock, but quickly realised that the ATTiny85 and 412 are very different beasts! Fortunately, digging through my parts bin, I found that I already had some ATTiny85's! I flashed the sample code to the ATTiny, using "Arduino as ISP", and implemented a simple 1-wire sketch for the same Arduino.
This resulted in a fairly roundabout test cycle:
1. Flash ArduinoISP onto the Arduino.
2. use the Arduino to flash the firmware onto the ATTiny85
3. Flash the Arduino 1-wire sketch onto the Arduino
4. goto 1
In retrospect, I should have just used two different Arduino's for the ISP and 1-wire sketch, it would have made my life a LOT easier!
Especially considering how many iterations it took me to get things working!
Firstly, I had tried it on an ESP32, to "prove" that the idea could work. The Arduino was able to enumerate the various 1-wire sensors that the ESP32 was emulating. However, when I flashed it to the ATTiny85, I got no results.
I put a logic analyser on the 1-wire pin to see what was happening, but the short answer was "nothing". The master would pull the line down, but the slave (ATTiny) simply never responded. Unfortunately, the ATTiny85 is rather resource limited, so trying to figure out what the problem could be seemed insurmountable.
Eventually, I realised that the sample sketch had a blink function on one of the other pins, so I included that in my logic analyser probe. And after an embarrassingly long time, I realised that the 0.5HZ (1 second on, 1 second off) flashing I was expecting to see was taking 16 seconds! And after some further googling, I found this note in the ATTinyCore documentation: https://github.com/SpenceKonde/ATTi...-you-are-not-using-the-chip-with-a-bootloader
And with that done, the ATTiny85 started responding to the master, and I could move my attention to the ADC half of the problem. A few more lines of code, and reference to https://github.com/kroesche/thermistor_lookup and https://mybroadband.co.za/forum/threads/geyserwise-temperature-probe.1181356/ (for the required constants), I had a working 1-wire slave, reporting temperatures read from the ADC.
And so, on to the THR320! This turned into an interesting exercise as well, as it boot-looped after being flashed with ESPHome. The documented workaround of installing Tasmota first didn't work for me at all. What did work for some weird reason was installing it with no wifi creds, but only ap: and captive_portal:. Then, powering it from AC allowed the device to be reconfigured onto my home WiFi, and reprogrammed OTA as usual.
Wanting to keep a physical failsafe, but still monitor the temperature was a problem. Having pondered all sorts of ways of putting a sensor inside the thermostat, but knowing that I also didn't really want to deal with any leaks if anything went wrong, I decided to go with a commercial product. I found the Geyserwise thermostat for sale by itself at an online store (normally only available as part of a much more comprehensive, and expensive, setup). This contains an NTC thermistor, which is an analog device, meant to form part of a voltage divider. Easy enough to work with, one would think!
The geyser has a 3kW element, which at 220V means a 20A relay should do the trick. First I got a CBI Astute Smart Controller, which is rated for 30A, and reprogrammed it using the LibreTuya-ESPHome project, since it is using a RTL8710BN microcontroller. However, my electrician told me that it could not be installed near to the geyser, as it was not an isolator. I then got the CBI Astute Smart Isolator, and did the same reprogramming. I then realised that the CBI Devices were not mains isolated at their GPIO's, and that connecting the external temperature sensor would potentially be routing 220V into the inside of my geyser! Time for a new approach, using something designed to use external sensors!
The best match I could find for this was the Sonoff THR320, which has a 20A relay, and a RJ9 plug for an external sensor. And if you look at the internals, there is an actual transformer stepping down mains voltage, and isolating the ESP32 in the process. Perfect! The downside, which I only figured out later, was that the exposed GPIO on the RJ9 port was connected to GPIO25, which is in the ADC2 group. Which is not usable if WiFi is in use. I considered a few options:
1. reroute GPIO25 to a GPIO in the ADC1 group. Problem: None of them were exposed on pins or pin headers, and the ESP32 is a VERY fine pitch package in amongst a number of other components, I don't trust my soldering enough to put a wire on the right pin!
2. Turn off the WiFi periodically, take the reading, and turn it back on again. Problem: I wasn't sure that this would work, and I didn't want to take chances with it failing in the wrong state.
3. Since the THR320 was designed for use with 1-wire sensors, somehow make the analog NTC thermistor appear to be a 1-wire sensor.
EDIT: 4. Another option that I only thought of later is to replace the thermistor entirely with a DS18B20 1-wire sensor at the end of the brass tube of the thermostat. This might require trimming the brass tube to allow enough space for the slightly larger component, and also needs 3 wires (in theory you can use 2, would probably also require some testing to be sure).
Googling for 1-wire slave implementations, I found a few, but the most promising was https://github.com/orgua/OneWireHub. This claimed to support a variety of microcontrollers, including the ATTiny85. I found a supplier with some ATTiny412's in stock, but quickly realised that the ATTiny85 and 412 are very different beasts! Fortunately, digging through my parts bin, I found that I already had some ATTiny85's! I flashed the sample code to the ATTiny, using "Arduino as ISP", and implemented a simple 1-wire sketch for the same Arduino.
This resulted in a fairly roundabout test cycle:
1. Flash ArduinoISP onto the Arduino.
2. use the Arduino to flash the firmware onto the ATTiny85
3. Flash the Arduino 1-wire sketch onto the Arduino
4. goto 1
In retrospect, I should have just used two different Arduino's for the ISP and 1-wire sketch, it would have made my life a LOT easier!
Especially considering how many iterations it took me to get things working!
Firstly, I had tried it on an ESP32, to "prove" that the idea could work. The Arduino was able to enumerate the various 1-wire sensors that the ESP32 was emulating. However, when I flashed it to the ATTiny85, I got no results.
I put a logic analyser on the 1-wire pin to see what was happening, but the short answer was "nothing". The master would pull the line down, but the slave (ATTiny) simply never responded. Unfortunately, the ATTiny85 is rather resource limited, so trying to figure out what the problem could be seemed insurmountable.
Eventually, I realised that the sample sketch had a blink function on one of the other pins, so I included that in my logic analyser probe. And after an embarrassingly long time, I realised that the 0.5HZ (1 second on, 1 second off) flashing I was expecting to see was taking 16 seconds! And after some further googling, I found this note in the ATTinyCore documentation: https://github.com/SpenceKonde/ATTi...-you-are-not-using-the-chip-with-a-bootloader
And with that done, the ATTiny85 started responding to the master, and I could move my attention to the ADC half of the problem. A few more lines of code, and reference to https://github.com/kroesche/thermistor_lookup and https://mybroadband.co.za/forum/threads/geyserwise-temperature-probe.1181356/ (for the required constants), I had a working 1-wire slave, reporting temperatures read from the ADC.
And so, on to the THR320! This turned into an interesting exercise as well, as it boot-looped after being flashed with ESPHome. The documented workaround of installing Tasmota first didn't work for me at all. What did work for some weird reason was installing it with no wifi creds, but only ap: and captive_portal:. Then, powering it from AC allowed the device to be reconfigured onto my home WiFi, and reprogrammed OTA as usual.
Attachments
Last edited:

