mirror of
https://github.com/openshwprojects/OpenBK7231T_App.git
synced 2026-02-10 10:45:45 +00:00
Hass discovery (#1122)
* HASS discovery energy stats fixed except energycounter_clear_date * HASS: add friendly entity names, remove timestamp class from energycounter_clear_date as workaround for hass-incompatible date format * HA energycounter_clear_date fixed for correct interpreting as home assistant timestamp sensor * refactor HA power sensors discovery info * refactor HA power sensors discovery more * add apparent power, reactive power, power factor to mqtt + hass discovery, refactor some vars into new energy_sensors[] struct * amend hass sensor unique_ids due to mqtt topic/channel too long; 'Error:MQTT:Unable to queue! Topic (13), channel (66) or value (437) exceeds size limit' * hass sensors: add 'energy 2 days ago', 'energy 3 days ago', 'uptime' web UI: energy sensors apply their rounding setting drv_bl_shared.c: add enum for daily_stats[], put rearrange energy_sensor[] struct to expose only names via DRV_GetEnergySensorNames() * -HA energy sensor uniq_id values made consistent with prior builds via .hass_uniq_id_suffix -Refactor drv_bl_shared sensor/counter vars into energy_sensors[] to simplify mqtt transmissions etc -Add energy '2 days ago'/'3 days ago' to main web ui, data from vars already being saved to/from flash -NTP fix html formatting in web ui * -HA energy sensor uniq_id values made consistent with prior builds via .hass_uniq_id_suffix -Refactor drv_bl_shared sensor/counter vars into energy_sensors[] to simplify mqtt transmissions etc -Add energy '2 days ago'/'3 days ago' to main web ui, data from vars already being saved to/from flash -NTP fix html formatting in web ui * Update settings.json ignore vscode settings... * Update settings.json * Update settings.json * minor fix * fix OBK_CONSUMPTION_LAST_HOUR missing from mqtt * HASS entity names use channel labels when set, hass discovery excludes unpublished entities (i.e. those set via SetChannelPrivate), hass discovery firmware build info added to diagnostic section, energy sensor discovery bugfix re clear-date * update submodule sdk * Fix ch0 label wrongly applied to diagnostic sensors * update docs --------- Co-authored-by: Stefan Smith <stefan064>
This commit is contained in:
@ -102,6 +102,9 @@ void hass_populate_unique_id(ENTITY_TYPE type, int index, char* uniq_id) {
|
||||
case HASS_UPTIME:
|
||||
sprintf(uniq_id, "%s_uptime", longDeviceName);
|
||||
break;
|
||||
case HASS_BUILD:
|
||||
sprintf(uniq_id, "%s_build", longDeviceName);
|
||||
break;
|
||||
default:
|
||||
// TODO: USE type here as well?
|
||||
// If type is not set, and we use "sensor" naming, we can easily make collision
|
||||
@ -189,7 +192,8 @@ cJSON* hass_build_device_node(cJSON* ids) {
|
||||
/// @brief Initializes HomeAssistant device discovery storage with common values.
|
||||
/// @param type
|
||||
/// @param index This is used to generate generate unique_id and name.
|
||||
/// It is ignored for RGB. For energy sensors, index corresponds to energySensor_t. For regular sensor, index can be be the channel.
|
||||
/// It is ignored for RGB and diagnostic sensors (HASS_RSSI, HASS_UPTIME, HASS_BUILD...).
|
||||
/// For energy sensors, index corresponds to energySensor_t. For regular sensor, index can be be the channel.
|
||||
/// @param payload_on The payload that represents enabled state. This is not added for POWER_SENSOR.
|
||||
/// @param payload_off The payload that represents disabled state. This is not added for POWER_SENSOR.
|
||||
/// @return
|
||||
@ -211,85 +215,92 @@ HassDeviceInfo* hass_init_device_info(ENTITY_TYPE type, int index, const char* p
|
||||
bool isSensor = false; //This does not count binary_sensor
|
||||
|
||||
//Build the `name`
|
||||
switch (type) {
|
||||
case LIGHT_ON_OFF:
|
||||
case LIGHT_PWM:
|
||||
case RELAY:
|
||||
case BINARY_SENSOR:
|
||||
if (CHANNEL_HasLabel(index) && type != ENERGY_METER_SENSOR) {
|
||||
sprintf(g_hassBuffer, "%s", CHANNEL_GetLabel(index));
|
||||
break;
|
||||
case LIGHT_PWMCW:
|
||||
case LIGHT_RGB:
|
||||
case LIGHT_RGBCW:
|
||||
//There can only be one RGB so we can skip including index in the name. Do the same
|
||||
//for 2 PWM case.
|
||||
sprintf(g_hassBuffer, "Light");
|
||||
break;
|
||||
case ENERGY_METER_SENSOR:
|
||||
isSensor = true;
|
||||
#ifndef OBK_DISABLE_ALL_DRIVERS
|
||||
if (index <= OBK__LAST)
|
||||
sprintf(g_hassBuffer, "%s", DRV_GetEnergySensorNames(index)->name_friendly);
|
||||
else
|
||||
sprintf(g_hassBuffer, "Unknown Energy Meter Sensor");
|
||||
#endif
|
||||
break;
|
||||
case POWER_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Power");
|
||||
break;
|
||||
case TEMPERATURE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Temperature");
|
||||
break;
|
||||
case HUMIDITY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Humidity");
|
||||
break;
|
||||
case CO2_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "CO2");
|
||||
break;
|
||||
case SMOKE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Smoke");
|
||||
break;
|
||||
case PRESSURE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Pressure");
|
||||
break;
|
||||
case TVOC_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Tvoc");
|
||||
break;
|
||||
case BATTERY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Battery");
|
||||
break;
|
||||
case BATTERY_VOLTAGE_SENSOR:
|
||||
case VOLTAGE_SENSOR:
|
||||
isSensor = (type == BATTERY_VOLTAGE_SENSOR);
|
||||
sprintf(g_hassBuffer, "Voltage");
|
||||
break;
|
||||
case ILLUMINANCE_SENSOR:
|
||||
sprintf(g_hassBuffer, "Illuminance");
|
||||
break;
|
||||
case HASS_RSSI:
|
||||
sprintf(g_hassBuffer, "RSSI");
|
||||
break;
|
||||
case HASS_UPTIME:
|
||||
sprintf(g_hassBuffer, "Uptime");
|
||||
break;
|
||||
case ENERGY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Energy");
|
||||
break;
|
||||
case TIMESTAMP_SENSOR:
|
||||
sprintf(g_hassBuffer, "Timestamp");
|
||||
break;
|
||||
default:
|
||||
sprintf(g_hassBuffer, "%s", CHANNEL_GetLabel(index));
|
||||
break;
|
||||
} else {
|
||||
switch (type) {
|
||||
case LIGHT_ON_OFF:
|
||||
case LIGHT_PWM:
|
||||
case RELAY:
|
||||
case BINARY_SENSOR:
|
||||
sprintf(g_hassBuffer, "%s", CHANNEL_GetLabel(index));
|
||||
break;
|
||||
case LIGHT_PWMCW:
|
||||
case LIGHT_RGB:
|
||||
case LIGHT_RGBCW:
|
||||
//There can only be one RGB so we can skip including index in the name. Do the same
|
||||
//for 2 PWM case.
|
||||
sprintf(g_hassBuffer, "Light");
|
||||
break;
|
||||
case ENERGY_METER_SENSOR:
|
||||
isSensor = true;
|
||||
#ifndef OBK_DISABLE_ALL_DRIVERS
|
||||
if (index <= OBK__LAST)
|
||||
sprintf(g_hassBuffer, "%s", DRV_GetEnergySensorNames(index)->name_friendly);
|
||||
else
|
||||
sprintf(g_hassBuffer, "Unknown Energy Meter Sensor");
|
||||
#endif
|
||||
break;
|
||||
case POWER_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Power");
|
||||
break;
|
||||
case TEMPERATURE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Temperature");
|
||||
break;
|
||||
case HUMIDITY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Humidity");
|
||||
break;
|
||||
case CO2_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "CO2");
|
||||
break;
|
||||
case SMOKE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Smoke");
|
||||
break;
|
||||
case PRESSURE_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Pressure");
|
||||
break;
|
||||
case TVOC_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Tvoc");
|
||||
break;
|
||||
case BATTERY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Battery");
|
||||
break;
|
||||
case BATTERY_VOLTAGE_SENSOR:
|
||||
case VOLTAGE_SENSOR:
|
||||
isSensor = (type == BATTERY_VOLTAGE_SENSOR);
|
||||
sprintf(g_hassBuffer, "Voltage");
|
||||
break;
|
||||
case ILLUMINANCE_SENSOR:
|
||||
sprintf(g_hassBuffer, "Illuminance");
|
||||
break;
|
||||
case HASS_RSSI:
|
||||
sprintf(g_hassBuffer, "RSSI");
|
||||
break;
|
||||
case HASS_UPTIME:
|
||||
sprintf(g_hassBuffer, "Uptime");
|
||||
break;
|
||||
case HASS_BUILD:
|
||||
sprintf(g_hassBuffer, "Build");
|
||||
break;
|
||||
case ENERGY_SENSOR:
|
||||
isSensor = true;
|
||||
sprintf(g_hassBuffer, "Energy");
|
||||
break;
|
||||
case TIMESTAMP_SENSOR:
|
||||
sprintf(g_hassBuffer, "Timestamp");
|
||||
break;
|
||||
default:
|
||||
sprintf(g_hassBuffer, "%s", CHANNEL_GetLabel(index));
|
||||
break;
|
||||
}
|
||||
}
|
||||
cJSON_AddStringToObject(info->root, "name", g_hassBuffer);
|
||||
cJSON_AddStringToObject(info->root, "~", CFG_GetMQTTClientId()); //base topic
|
||||
@ -653,13 +664,17 @@ HassDeviceInfo* hass_init_sensor_device_info(ENTITY_TYPE type, int channel, int
|
||||
cJSON_AddStringToObject(info->root, "entity_category", "diagnostic");
|
||||
cJSON_AddStringToObject(info->root, "stat_cla", "total_increasing");
|
||||
break;
|
||||
case HASS_BUILD:
|
||||
cJSON_AddStringToObject(info->root, "stat_t", "~/build");
|
||||
cJSON_AddStringToObject(info->root, "entity_category", "diagnostic");
|
||||
break;
|
||||
default:
|
||||
sprintf(g_hassBuffer, "~/%d/get", channel);
|
||||
cJSON_AddStringToObject(info->root, "stat_t", g_hassBuffer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (type != READONLYLOWMIDHIGH_SENSOR && !cJSON_HasObjectItem(info->root, "stat_cla")) {
|
||||
if (type != READONLYLOWMIDHIGH_SENSOR && type != HASS_BUILD && !cJSON_HasObjectItem(info->root, "stat_cla")) {
|
||||
cJSON_AddStringToObject(info->root, "stat_cla", "measurement");
|
||||
}
|
||||
|
||||
|
||||
@ -69,6 +69,8 @@ typedef enum {
|
||||
HASS_RSSI,
|
||||
/// @brief Time firmware is alive in secs
|
||||
HASS_UPTIME,
|
||||
/// @brief Firmware build info
|
||||
HASS_BUILD,
|
||||
/// @brief Wh, kWh
|
||||
ENERGY_SENSOR,
|
||||
// hPa
|
||||
|
||||
@ -1577,6 +1577,7 @@ void doHomeAssistantDiscovery(const char* topic, http_request_t* request) {
|
||||
int relayCount;
|
||||
int pwmCount;
|
||||
int dInputCount;
|
||||
int excludedCount = 0;
|
||||
bool ledDriverChipRunning;
|
||||
HassDeviceInfo* dev_info = NULL;
|
||||
bool measuringPower = false;
|
||||
@ -1592,6 +1593,13 @@ void doHomeAssistantDiscovery(const char* topic, http_request_t* request) {
|
||||
// no channels published yet
|
||||
flagsChannelPublished = 0;
|
||||
|
||||
for (i = 0; i < CHANNEL_MAX; i++) {
|
||||
if (CHANNEL_HasNeverPublishFlag(i)) {
|
||||
BIT_SET(flagsChannelPublished, i);
|
||||
excludedCount++;
|
||||
}
|
||||
}
|
||||
|
||||
if (topic == 0 || *topic == 0) {
|
||||
topic = "homeassistant";
|
||||
}
|
||||
@ -1602,7 +1610,7 @@ void doHomeAssistantDiscovery(const char* topic, http_request_t* request) {
|
||||
#endif
|
||||
|
||||
PIN_get_Relay_PWM_Count(&relayCount, &pwmCount, &dInputCount);
|
||||
addLogAdv(LOG_INFO, LOG_FEATURE_HTTP, "HASS counts: %i rels, %i pwms, %i inps", relayCount, pwmCount, dInputCount);
|
||||
addLogAdv(LOG_INFO, LOG_FEATURE_HTTP, "HASS counts: %i rels, %i pwms, %i inps, %i excluded", relayCount, pwmCount, dInputCount, excludedCount);
|
||||
|
||||
ledDriverChipRunning = LED_IsLedDriverChipRunning();
|
||||
|
||||
@ -1739,7 +1747,7 @@ void doHomeAssistantDiscovery(const char* topic, http_request_t* request) {
|
||||
|
||||
#ifndef OBK_DISABLE_ALL_DRIVERS
|
||||
if (measuringPower == true) {
|
||||
for (i = OBK__FIRST; i < OBK__LAST; i++)
|
||||
for (i = OBK__FIRST; i <= OBK__LAST; i++)
|
||||
{
|
||||
dev_info = hass_init_energy_sensor_device_info(i);
|
||||
if (dev_info) {
|
||||
@ -2047,10 +2055,14 @@ void doHomeAssistantDiscovery(const char* topic, http_request_t* request) {
|
||||
}
|
||||
#endif
|
||||
if (1) {
|
||||
dev_info = hass_init_sensor_device_info(HASS_RSSI, 0, -1, -1, 1);
|
||||
//use -1 for channel as these don't correspond to channels
|
||||
dev_info = hass_init_sensor_device_info(HASS_RSSI, -1, -1, -1, 1);
|
||||
MQTT_QueuePublish(topic, dev_info->channel, hass_build_discovery_json(dev_info), OBK_PUBLISH_FLAG_RETAIN);
|
||||
hass_free_device_info(dev_info);
|
||||
dev_info = hass_init_sensor_device_info(HASS_UPTIME, 0, -1, -1, 1);
|
||||
dev_info = hass_init_sensor_device_info(HASS_UPTIME, -1, -1, -1, 1);
|
||||
MQTT_QueuePublish(topic, dev_info->channel, hass_build_discovery_json(dev_info), OBK_PUBLISH_FLAG_RETAIN);
|
||||
hass_free_device_info(dev_info);
|
||||
dev_info = hass_init_sensor_device_info(HASS_BUILD, -1, -1, -1, 1);
|
||||
MQTT_QueuePublish(topic, dev_info->channel, hass_build_discovery_json(dev_info), OBK_PUBLISH_FLAG_RETAIN);
|
||||
hass_free_device_info(dev_info);
|
||||
discoveryQueued = true;
|
||||
|
||||
Reference in New Issue
Block a user