I have an Arduino code that is an impossible task for me to configure to discover an MQTT device in Home Assistant. In desperation, I even tried the AI’s help as a last resort, but as expected, it is also stupid and device detection simply does not work. I see separate sensors, so the MQTT connection per se is fine, I’m also not a C++ coder, so the only option is if someone here finds this error and fixes it.
Thanks
#include <ESP8266WiFi.h>
#include <PubSubClient.h>
// Wi-Fi credentials
const char* ssid = "your_ssid"; // Replace with your Wi-Fi SSID
const char* password = "your_password"; // Replace with your Wi-Fi password
// MQTT broker information
const char* mqtt_server = "your_mqtt_broker_ip"; // Replace with your MQTT broker IP
const int mqtt_port = 1883; // Default MQTT port
const char* mqtt_user = "your_mqtt_username"; // Replace with your MQTT broker username
const char* mqtt_password = "your_mqtt_password"; // Replace with your MQTT broker password
WiFiClient espClient;
PubSubClient client(espClient);
// Device and MQTT settings
const char* device_name = "Hewalex_Solar";
const char* mqtt_topic_base = "homeassistant/sensor/hewalex_solar";
const char* node_id = "hewalex_solar"; // Node ID for MQTT discovery
float Temp[8];
// Wi-Fi Setup
void setup_wifi() {
delay(10);
Serial.println();
Serial.print("Connecting to ");
Serial.println(ssid);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("");
Serial.println("WiFi connected");
Serial.println("IP address: ");
Serial.println(WiFi.localIP());
}
// MQTT Callback (not used here)
void mqttCallback(char* topic, byte* payload, unsigned int length) {
// Handle incoming MQTT messages
}
// Reconnect to MQTT broker
void reconnect() {
// Loop until reconnected
while (!client.connected()) {
Serial.print("Attempting MQTT connection...");
// Attempt to connect
if (client.connect(device_name, mqtt_user, mqtt_password)) {
Serial.println("connected");
// Publish MQTT discovery messages for Home Assistant
publishDiscoveryMessages();
} else {
Serial.print("failed, rc=");
Serial.print(client.state());
Serial.println(" try again in 5 seconds");
delay(5000);
}
}
}
// Publish discovery messages for Home Assistant
void publishDiscoveryMessages() {
// Device information for grouping
String deviceInfo =
"{\"identifiers\": [\"hewalex_solar_device\"],"
"\"name\": \"Hewalex Solar System\","
"\"model\": \"Hewalex Model X\","
"\"manufacturer\": \"Hewalex\","
"\"sw_version\": \"1.0\","
"\"support_url\": \"https://hewalex.com/support\"}";
// Discovery topics for each sensor
String discoveryTopics[] = {
String("homeassistant/sensor/") + node_id + "/collector_temp/config", // Renamed to Collector Temp
String("homeassistant/sensor/") + node_id + "/buffer_temp/config", // Renamed to Buffer Temp
String("homeassistant/sensor/") + node_id + "/temperature2/config",
String("homeassistant/sensor/") + node_id + "/temperature3/config",
String("homeassistant/sensor/") + node_id + "/temperature4/config",
String("homeassistant/sensor/") + node_id + "/temperature5/config",
String("homeassistant/sensor/") + node_id + "/pump_rpm/config",
String("homeassistant/sensor/") + node_id + "/temperature7/config"
};
// Sensor names
String sensorNames[] = {
"Hewalex Solar Collector Temp", // Renamed
"Hewalex Solar Buffer Temp", // Renamed
"Hewalex Solar Temperature 2",
"Hewalex Solar Temperature 3",
"Hewalex Solar Temperature 4",
"Hewalex Solar Temperature 5",
"Hewalex Solar Pump RPM",
"Hewalex Solar Temperature 7"
};
// Units of measurement
String units[] = {
"°C", "°C", "°C", "°C", "°C", "°C", "RPM", "°C"
};
// JSON keys
String jsonKeys[] = {
"collector_temp", "buffer_temp", "temperature2", // Renamed JSON keys
"temperature3", "temperature4", "temperature5",
"pump_rpm", "temperature7"
};
// Unique IDs
String uniqueIds[] = {
"hewalex_collector_temp", // Unique ID for Collector Temp
"hewalex_buffer_temp", // Unique ID for Buffer Temp
"hewalex_temperature2",
"hewalex_temperature3",
"hewalex_temperature4",
"hewalex_temperature5",
"hewalex_pump_rpm",
"hewalex_temperature7"
};
// Publish discovery messages
for (int i = 0; i < 8; i++) {
String discoveryPayload = String("{") +
"\"name\": \"" + sensorNames[i] + "\"," +
"\"state_topic\": \"" + mqtt_topic_base + "\"," +
"\"unit_of_measurement\": \"" + units[i] + "\"," +
"\"value_template\": \"{{ value_json." + jsonKeys[i] + " }}\"," +
"\"device\": " + deviceInfo + "," +
"\"unique_id\": \"" + uniqueIds[i] + "\"" +
"}";
client.publish(discoveryTopics[i].c_str(), discoveryPayload.c_str(), true);
Serial.print("Published discovery message for ");
Serial.println(sensorNames[i]);
}
}
void setup() {
// Initialize Serial Monitor for debugging
Serial.begin(115200);
// Initialize Wi-Fi
setup_wifi();
// Initialize MQTT client
client.setServer(mqtt_server, mqtt_port); // Set MQTT broker with port
client.setCallback(mqttCallback);
// Initialize hardware Serial for RS485 communication
Serial.begin(38400); // Set the baud rate for RS485 communication
}
void loop() {
if (!client.connected()) {
reconnect();
}
client.loop();
char messageread[1000]; // Buffer to store incoming data
int pos = 0; // Position index for message buffer
// Define the message to be sent via RS485
byte message[] = {0x69, 0x02, 0x01, 0x84, 0x00, 0x00, 0x0C, 0xF6, 0x02, 0x00, 0x01, 0x00, 0x40, 0x80, 0x00, 0x32, 0x64, 0x00, 0xBD, 0xB2};
// Send the message via RS485
Serial.write(message, sizeof(message)); // Send the message via RS485
// Delay to allow message transmission
delay(10);
// Read the data coming in from RS485
while (Serial.available() > 0) {
messageread[pos] = Serial.read();
pos++;
}
// Check the first byte to ensure the correct message was received
if (messageread[0] == 0x69) {
int fncID = messageread[12]; // Extract function ID
// Process message if function ID matches expected value
if (fncID == 0x50) {
int startReg = messageread[16]; // Extract starting register
for (int i = 0; i < messageread[15]; i++) {
if (i % 2 == 0) {
int iReg = i + startReg; // Calculate register index
// Process temperature readings based on register index
if (iReg == 128) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[0] = w / 10.0; // Collector Temp
}
if (iReg == 130) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[1] = (w / 10.0) * 10.0; // Buffer Temp
}
if (iReg == 132) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[2] = (w / 10.0) * 10.0; // Adjust Temperature 2 for correct decimal
}
if (iReg == 138) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[3] = w / 10.0;
}
if (iReg == 140) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[4] = w / 10.0;
}
if (iReg == 142) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[5] = w / 10.0;
}
if (iReg == 144) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[6] = w; // Use Temp[6] as pump RPM directly
}
if (iReg == 146) {
byte hexstr[] = {messageread[19 + i], messageread[18 + i]};
int w = hexstr[0] << 8 | hexstr[1];
if (w & 0x8000) {
w = w - 0x10000;
}
Temp[7] = w / 10.0;
}
}
}
}
}
// Send temperature data and pump RPM to MQTT
char mqttPayload[256];
snprintf(mqttPayload, sizeof(mqttPayload),
"{\"collector_temp\": %.1f, \"buffer_temp\": %.1f, \"temperature2\": %.1f, \"temperature3\": %.1f, \"temperature4\": %.1f, \"temperature5\": %.1f, \"pump_rpm\": %.0f, \"temperature7\": %.1f}",
Temp[0], Temp[1], Temp[2], Temp[3], Temp[4], Temp[5], Temp[6], Temp[7]);
client.publish(mqtt_topic_base, mqttPayload);
// Print renamed readings and pump RPM to Serial Monitor
Serial.print("Collector Temp = ");
Serial.print(Temp[0]);
Serial.println(" °C");
Serial.print("Buffer Temp = ");
Serial.print(Temp[1]);
Serial.println(" °C");
for (int i = 2; i < 8; i++) {
if (i == 6) {
Serial.print("Pump RPM = "); // Output Temp[6] as pump RPM
Serial.print(Temp[6]);
Serial.println(" RPM");
} else {
Serial.print("Temperature ");
Serial.print(i);
Serial.print(" = ");
Serial.print(Temp[i]);
Serial.println(" °C");
}
}
// Wait for 2 seconds before repeating
delay(2000);
}