No description
| docs | ||
| .gitignore | ||
| AGENTS.md | ||
| README.md | ||
| zealux-heatpump.yaml | ||
Zealux Heat Pump → Home Assistant
An ESPHome integration for the Zealux Inverboost Classic Plus R290 heat pump (model XAH07Csi9). An Olimex ESP32-POE-ISO (Ethernet + PoE) polls and drives the heat pump's mainboard over Modbus RTU / RS485 and exposes all entities to Home Assistant via the native ESPHome API — no cloud, no WiFi module required.
The register map comes from the Huizhou Dahua 0760 MODBUS Protocol Specification V1.7, stored
in this repo under docs/.
Hardware
| Part | Notes |
|---|---|
| Olimex ESP32-POE-ISO | Ethernet (LAN8720 PHY) + PoE power |
| TTL-RS485 module (auto-flow-control) | No DE/RE pin needed |
| PoE injector or PoE switch port | Powers the ESP32 over the ethernet run |
Wiring
Heat pump mainboard RS485 port: 4-pin JST connector, pinout A | B | G | +12V
- A / B → RS485 data lines of the converter (swap A/B if you get no response)
- G → GND
- +12V → unused; the ESP32 is powered via PoE
GPIO notes
- UART: GPIO32 (TX) / GPIO33 (RX) — free on the ESP32-POE-ISO EXT2 header
- The ethernet PHY claims GPIO0/12/17/18/23 — do not use these for anything else
- This config assumes the WROOM module. On WROVER variants the PSRAM
claims GPIO16/17: the PHY clock moves to GPIO0 and GPIO33 is repurposed —
change
clk.pinto GPIO0 and pick another UART RX pin - If your board revision differs, adjust the pins in
zealux-heatpump.yaml
Protocol
- RS485, Modbus RTU, 9600 baud, 8 data bits, EVEN parity, 1 stop bit
- Slave address 0x01 (default; settable via the line controller)
- Function codes: 03 (read holding), 06 (write single), 10 (write multiple)
- Max 38 registers per read/write block, addresses must be contiguous
- Temperature / current registers are x10 scaled (multiply by 0.1)
- Settings block:
0x0000–0x0027(RW) - Measurement block:
0x0030–0x006A(R); ESPHome auto-groups the defined addresses into contiguous reads (all well under the 38-register limit) 0x0045status flags and0x0046/0x0047fault bitfields map to the panel E-codes (bit meanings are documented in thezealux-heatpump.yamlcomments)
Entities
Polling runs every 10 s. Provided entities:
- Switch — Power (
0x0000) - Select — Operating mode (
0x0001): Hot water + auto heating, Room heating, Hot water, Room cooling, Hot water + auto cooling - Numbers — Hot water setpoint (
0x0002, 20–55 °C), Heating setpoint (0x0003, 15–45 °C), Cooling setpoint (0x0004, 5–35 °C), Hot water hysteresis (0x0005), Heating-cooling hysteresis (0x0006) - Sensors
- Operating state: compressor frequency (
0x0031), target frequency (0x0041), operating current (0x0032) - Temperatures (all x10): return water, hot water, supply pipe, discharge, outdoor ambient, outdoor coil, return gas, after throttling
- Electrical: EEV opening (
0x003C), DC bus voltage (0x004A), AC input voltage (0x004B), AC input power (0x004C), compressor phase current (0x004E) - Misc: IPM module temperature (
0x0043), water pump duty cycle (0x0049) - Diagnostics (raw bitfields): protect code, shutdown code, status flags, fault symbols 1/2
- Operating state: compressor frequency (
- Binary sensors — Defrosting, Water pump running, Fault present
- Text sensor — Operating mode (reported), decoded via lambda
Build & flash
# Validate config
esphome config zealux-heatpump.yaml
# Compile
esphome compile zealux-heatpump.yaml
# First flash over USB (board has no firmware yet)
esphome run zealux-heatpump.yaml
# OTA afterwards: via ESPHome dashboard / HA add-on
Logs go over Ethernet/API (logger.baud_rate: 0 disables USB-serial logging;
the Modbus UART lives on GPIO32/33 regardless).
Gotchas & to-verify
- The built-in Tuya WiFi module is also a Modbus master on this bus (FC 5AH in the spec). Decision: disconnect it; the ESP32 becomes the sole master and the cloud app is lost.
- AC input power (
0x004C), AC voltage (0x004B), DC bus voltage (0x004A) and IPM temp (0x0043) have no documented scale in the spec. Verify empirically against the panel display / a meter and adjust filters. - Values marked per-flag-description tables (mode, faults) live in the
zealux-heatpump.yamlcomments.
Safety conventions
- Read-only sensors stay read-only; never write defrost/hysteresis registers from automations.
- Writes are only to: power (
0x0000), mode (0x0001), setpoints (0x0002–0x0006).