ESPHome 2026.10.0-dev
Loading...
Searching...
No Matches
growatt_solar.cpp
Go to the documentation of this file.
1#include "growatt_solar.h"
2#include "esphome/core/log.h"
3
5
6namespace helpers = modbus::helpers;
7
8static const char *const TAG = "growatt_solar";
9
10static const uint8_t MODBUS_REGISTER_COUNT[] = {33, 95}; // indexed with enum GrowattProtocolVersion
11
12void GrowattSolar::update() { this->read_input_registers(0, MODBUS_REGISTER_COUNT[this->protocol_version_]); }
13
14void GrowattSolar::on_read_input_registers(uint16_t start_address, std::span<const uint16_t> registers,
17 return;
18
19 // Publish a sensor if its register(s) are in this response; skipping absent registers keeps this
20 // correct for any read range, so the poll may be split into multiple requests.
21 auto publish_1_reg_sensor_state = [&](sensor::Sensor *sensor, uint16_t reg, float unit) -> void {
22 if (sensor == nullptr)
23 return;
25 sensor->publish_state(*value * unit);
26 };
27
28 auto publish_2_reg_sensor_state = [&](sensor::Sensor *sensor, uint16_t reg, float unit) -> void {
29 if (sensor == nullptr)
30 return;
32 sensor->publish_state(*value * unit);
33 };
34
35 switch (this->protocol_version_) {
36 case RTU: {
37 publish_1_reg_sensor_state(this->inverter_status_, RTU_INVERTER_STATUS, 1);
38
39 publish_2_reg_sensor_state(this->pv_active_power_sensor_, RTU_PV_ACTIVE_POWER, ONE_DEC_UNIT);
40
41 publish_1_reg_sensor_state(this->pvs_[0].voltage_sensor_, RTU_PV1_VOLTAGE, ONE_DEC_UNIT);
42 publish_1_reg_sensor_state(this->pvs_[0].current_sensor_, RTU_PV1_CURRENT, ONE_DEC_UNIT);
43 publish_2_reg_sensor_state(this->pvs_[0].active_power_sensor_, RTU_PV1_ACTIVE_POWER, ONE_DEC_UNIT);
44
45 publish_1_reg_sensor_state(this->pvs_[1].voltage_sensor_, RTU_PV2_VOLTAGE, ONE_DEC_UNIT);
46 publish_1_reg_sensor_state(this->pvs_[1].current_sensor_, RTU_PV2_CURRENT, ONE_DEC_UNIT);
47 publish_2_reg_sensor_state(this->pvs_[1].active_power_sensor_, RTU_PV2_ACTIVE_POWER, ONE_DEC_UNIT);
48
49 publish_2_reg_sensor_state(this->grid_active_power_sensor_, RTU_GRID_ACTIVE_POWER, ONE_DEC_UNIT);
50 publish_1_reg_sensor_state(this->grid_frequency_sensor_, RTU_GRID_FREQUENCY, TWO_DEC_UNIT);
51
52 publish_1_reg_sensor_state(this->phases_[0].voltage_sensor_, RTU_PHASE1_VOLTAGE, ONE_DEC_UNIT);
53 publish_1_reg_sensor_state(this->phases_[0].current_sensor_, RTU_PHASE1_CURRENT, ONE_DEC_UNIT);
54 publish_2_reg_sensor_state(this->phases_[0].active_power_sensor_, RTU_PHASE1_ACTIVE_POWER, ONE_DEC_UNIT);
55
56 publish_1_reg_sensor_state(this->phases_[1].voltage_sensor_, RTU_PHASE2_VOLTAGE, ONE_DEC_UNIT);
57 publish_1_reg_sensor_state(this->phases_[1].current_sensor_, RTU_PHASE2_CURRENT, ONE_DEC_UNIT);
58 publish_2_reg_sensor_state(this->phases_[1].active_power_sensor_, RTU_PHASE2_ACTIVE_POWER, ONE_DEC_UNIT);
59
60 publish_1_reg_sensor_state(this->phases_[2].voltage_sensor_, RTU_PHASE3_VOLTAGE, ONE_DEC_UNIT);
61 publish_1_reg_sensor_state(this->phases_[2].current_sensor_, RTU_PHASE3_CURRENT, ONE_DEC_UNIT);
62 publish_2_reg_sensor_state(this->phases_[2].active_power_sensor_, RTU_PHASE3_ACTIVE_POWER, ONE_DEC_UNIT);
63
64 publish_2_reg_sensor_state(this->today_production_, RTU_TODAY_PRODUCTION, ONE_DEC_UNIT);
65 publish_2_reg_sensor_state(this->total_energy_production_, RTU_TOTAL_ENERGY_PRODUCTION, ONE_DEC_UNIT);
66
67 publish_1_reg_sensor_state(this->inverter_module_temp_, RTU_INVERTER_MODULE_TEMP, ONE_DEC_UNIT);
68 break;
69 }
70 case RTU2: {
71 publish_1_reg_sensor_state(this->inverter_status_, RTU2_INVERTER_STATUS, 1);
72
73 publish_2_reg_sensor_state(this->pv_active_power_sensor_, RTU2_PV_ACTIVE_POWER, ONE_DEC_UNIT);
74
75 publish_1_reg_sensor_state(this->pvs_[0].voltage_sensor_, RTU2_PV1_VOLTAGE, ONE_DEC_UNIT);
76 publish_1_reg_sensor_state(this->pvs_[0].current_sensor_, RTU2_PV1_CURRENT, ONE_DEC_UNIT);
77 publish_2_reg_sensor_state(this->pvs_[0].active_power_sensor_, RTU2_PV1_ACTIVE_POWER, ONE_DEC_UNIT);
78
79 publish_1_reg_sensor_state(this->pvs_[1].voltage_sensor_, RTU2_PV2_VOLTAGE, ONE_DEC_UNIT);
80 publish_1_reg_sensor_state(this->pvs_[1].current_sensor_, RTU2_PV2_CURRENT, ONE_DEC_UNIT);
81 publish_2_reg_sensor_state(this->pvs_[1].active_power_sensor_, RTU2_PV2_ACTIVE_POWER, ONE_DEC_UNIT);
82
83 publish_2_reg_sensor_state(this->grid_active_power_sensor_, RTU2_GRID_ACTIVE_POWER, ONE_DEC_UNIT);
84 publish_1_reg_sensor_state(this->grid_frequency_sensor_, RTU2_GRID_FREQUENCY, TWO_DEC_UNIT);
85
86 publish_1_reg_sensor_state(this->phases_[0].voltage_sensor_, RTU2_PHASE1_VOLTAGE, ONE_DEC_UNIT);
87 publish_1_reg_sensor_state(this->phases_[0].current_sensor_, RTU2_PHASE1_CURRENT, ONE_DEC_UNIT);
88 publish_2_reg_sensor_state(this->phases_[0].active_power_sensor_, RTU2_PHASE1_ACTIVE_POWER, ONE_DEC_UNIT);
89
90 publish_1_reg_sensor_state(this->phases_[1].voltage_sensor_, RTU2_PHASE2_VOLTAGE, ONE_DEC_UNIT);
91 publish_1_reg_sensor_state(this->phases_[1].current_sensor_, RTU2_PHASE2_CURRENT, ONE_DEC_UNIT);
92 publish_2_reg_sensor_state(this->phases_[1].active_power_sensor_, RTU2_PHASE2_ACTIVE_POWER, ONE_DEC_UNIT);
93
94 publish_1_reg_sensor_state(this->phases_[2].voltage_sensor_, RTU2_PHASE3_VOLTAGE, ONE_DEC_UNIT);
95 publish_1_reg_sensor_state(this->phases_[2].current_sensor_, RTU2_PHASE3_CURRENT, ONE_DEC_UNIT);
96 publish_2_reg_sensor_state(this->phases_[2].active_power_sensor_, RTU2_PHASE3_ACTIVE_POWER, ONE_DEC_UNIT);
97
98 publish_2_reg_sensor_state(this->today_production_, RTU2_TODAY_PRODUCTION, ONE_DEC_UNIT);
99 publish_2_reg_sensor_state(this->total_energy_production_, RTU2_TOTAL_ENERGY_PRODUCTION, ONE_DEC_UNIT);
100
101 publish_1_reg_sensor_state(this->inverter_module_temp_, RTU2_INVERTER_MODULE_TEMP, ONE_DEC_UNIT);
102 break;
103 }
104 }
105}
106
108 ESP_LOGCONFIG(TAG,
109 "GROWATT Solar:\n"
110 " Address: 0x%02X",
111 this->address_);
112}
113
114} // namespace esphome::growatt_solar
uint8_t status
Definition bl0942.h:8
struct esphome::growatt_solar::GrowattSolar::GrowattPhase phases_[3]
GrowattProtocolVersion protocol_version_
struct esphome::growatt_solar::GrowattSolar::GrowattPV pvs_[2]
void on_read_input_registers(uint16_t start_address, std::span< const uint16_t > registers, modbus::ResponseStatus status) override
Base-class for all sensors.
Definition sensor.h:47
void publish_state(float state)
Publish a new state to the front-end.
Definition sensor.cpp:68
constexpr uint16_t RTU2_INVERTER_STATUS
constexpr uint16_t RTU_PV1_ACTIVE_POWER
constexpr uint16_t RTU_GRID_ACTIVE_POWER
constexpr uint16_t RTU_PHASE2_VOLTAGE
constexpr uint16_t RTU_PHASE3_VOLTAGE
constexpr uint16_t RTU_TODAY_PRODUCTION
constexpr uint16_t RTU2_INVERTER_MODULE_TEMP
constexpr uint16_t RTU_INVERTER_MODULE_TEMP
constexpr uint16_t RTU2_TODAY_PRODUCTION
constexpr uint16_t RTU2_PHASE2_CURRENT
constexpr uint16_t RTU2_PHASE3_VOLTAGE
constexpr uint16_t RTU_PV2_VOLTAGE
constexpr uint16_t RTU2_GRID_ACTIVE_POWER
constexpr uint16_t RTU_INVERTER_STATUS
constexpr uint16_t RTU2_PV2_CURRENT
constexpr uint16_t RTU_PV1_VOLTAGE
constexpr uint16_t RTU2_PV1_CURRENT
constexpr uint16_t RTU_PV_ACTIVE_POWER
constexpr uint16_t RTU2_PV2_ACTIVE_POWER
constexpr uint16_t RTU2_PV2_VOLTAGE
constexpr uint16_t RTU_PHASE3_CURRENT
constexpr uint16_t RTU_TOTAL_ENERGY_PRODUCTION
constexpr uint16_t RTU2_PHASE1_ACTIVE_POWER
constexpr uint16_t RTU_GRID_FREQUENCY
constexpr uint16_t RTU2_PHASE1_VOLTAGE
constexpr uint16_t RTU2_PHASE2_ACTIVE_POWER
constexpr uint16_t RTU2_GRID_FREQUENCY
constexpr uint16_t RTU_PHASE1_ACTIVE_POWER
constexpr uint16_t RTU_PHASE1_CURRENT
constexpr uint16_t RTU2_PHASE1_CURRENT
constexpr uint16_t RTU2_PHASE3_ACTIVE_POWER
constexpr uint16_t RTU_PV2_ACTIVE_POWER
constexpr uint16_t RTU2_PHASE3_CURRENT
constexpr uint16_t RTU2_TOTAL_ENERGY_PRODUCTION
constexpr uint16_t RTU2_PV1_VOLTAGE
constexpr uint16_t RTU_PV2_CURRENT
constexpr uint16_t RTU2_PV1_ACTIVE_POWER
constexpr uint16_t RTU_PHASE2_CURRENT
constexpr uint16_t RTU_PHASE2_ACTIVE_POWER
constexpr uint16_t RTU_PHASE1_VOLTAGE
constexpr uint16_t RTU_PV1_CURRENT
constexpr uint16_t RTU2_PV_ACTIVE_POWER
constexpr uint16_t RTU_PHASE3_ACTIVE_POWER
constexpr uint16_t RTU2_PHASE2_VOLTAGE
constexpr std::optional< RegisterValueType< VALUE_TYPE > > value_at(std::span< const uint16_t > registers, uint16_t start_address, uint16_t address)
The value stored at an absolute register address, or nullopt when it is not wholly inside this respon...
std::optional< ExceptionCode > ResponseStatus
Definition modbus.h:306
bool succeeded(ResponseStatus status)
True when a transaction carried no exception.
Definition modbus.h:309