|
|
@ -15,6 +15,7 @@ |
|
|
|
#include <WiFi.h> |
|
|
|
#endif |
|
|
|
|
|
|
|
#include <array> |
|
|
|
#include "../utils/dbg.h" |
|
|
|
#include "../config/config.h" |
|
|
|
#include <espMqttClient.h> |
|
|
@ -38,12 +39,15 @@ template<class HMSYSTEM> |
|
|
|
class PubMqtt { |
|
|
|
public: |
|
|
|
PubMqtt() { |
|
|
|
mRxCnt = 0; |
|
|
|
mTxCnt = 0; |
|
|
|
mSubscriptionCb = NULL; |
|
|
|
memset(mLastIvState, (uint8_t)InverterStatus::OFF, MAX_NUM_INVERTERS); |
|
|
|
memset(mIvLastRTRpub, 0, MAX_NUM_INVERTERS * 4); |
|
|
|
mLastAnyAvail = false; |
|
|
|
mLastIvState.fill(InverterStatus::OFF); |
|
|
|
mIvLastRTRpub.fill(0); |
|
|
|
|
|
|
|
mVal.fill(0); |
|
|
|
mTopic.fill(0); |
|
|
|
mSubTopic.fill(0); |
|
|
|
mClientId.fill(0); |
|
|
|
mLwtTopic.fill(0); |
|
|
|
mSendAlarm.fill(false); |
|
|
|
} |
|
|
|
|
|
|
|
~PubMqtt() { } |
|
|
@ -63,16 +67,16 @@ class PubMqtt { |
|
|
|
}); |
|
|
|
mDiscovery.running = false; |
|
|
|
|
|
|
|
snprintf(mLwtTopic, MQTT_TOPIC_LEN + 5, "%s/mqtt", mCfgMqtt->topic); |
|
|
|
snprintf(mLwtTopic.data(), mLwtTopic.size(), "%s/mqtt", mCfgMqtt->topic); |
|
|
|
|
|
|
|
if((strlen(mCfgMqtt->user) > 0) && (strlen(mCfgMqtt->pwd) > 0)) |
|
|
|
mClient.setCredentials(mCfgMqtt->user, mCfgMqtt->pwd); |
|
|
|
|
|
|
|
if(strlen(mCfgMqtt->clientId) > 0) |
|
|
|
snprintf(mClientId, 23, "%s", mCfgMqtt->clientId); |
|
|
|
snprintf(mClientId.data(), mClientId.size(), "%s", mCfgMqtt->clientId); |
|
|
|
else { |
|
|
|
snprintf(mClientId, 23, "%s-", mDevName); |
|
|
|
uint8_t pos = strlen(mClientId); |
|
|
|
snprintf(mClientId.data(), mClientId.size(), "%s-", mDevName); |
|
|
|
uint8_t pos = strlen(mClientId.data()); |
|
|
|
mClientId[pos++] = WiFi.macAddress().substring( 9, 10).c_str()[0]; |
|
|
|
mClientId[pos++] = WiFi.macAddress().substring(10, 11).c_str()[0]; |
|
|
|
mClientId[pos++] = WiFi.macAddress().substring(12, 13).c_str()[0]; |
|
|
@ -82,9 +86,9 @@ class PubMqtt { |
|
|
|
mClientId[pos++] = '\0'; |
|
|
|
} |
|
|
|
|
|
|
|
mClient.setClientId(mClientId); |
|
|
|
mClient.setClientId(mClientId.data()); |
|
|
|
mClient.setServer(mCfgMqtt->broker, mCfgMqtt->port); |
|
|
|
mClient.setWill(mLwtTopic, QOS_0, true, mqttStr[MQTT_STR_LWT_NOT_CONN]); |
|
|
|
mClient.setWill(mLwtTopic.data(), QOS_0, true, mqttStr[MQTT_STR_LWT_NOT_CONN]); |
|
|
|
mClient.onConnect(std::bind(&PubMqtt::onConnect, this, std::placeholders::_1)); |
|
|
|
mClient.onDisconnect(std::bind(&PubMqtt::onDisconnect, this, std::placeholders::_1)); |
|
|
|
mClient.onMessage(std::bind(&PubMqtt::onMessage, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4, std::placeholders::_5, std::placeholders::_6)); |
|
|
@ -125,8 +129,8 @@ class PubMqtt { |
|
|
|
} |
|
|
|
|
|
|
|
void tickerMinute() { |
|
|
|
snprintf(mVal, 40, "%d", (*mUptime)); |
|
|
|
publish(subtopics[MQTT_UPTIME], mVal); |
|
|
|
snprintf(mVal.data(), mVal.size(), "%u", (*mUptime)); |
|
|
|
publish(subtopics[MQTT_UPTIME], mVal.data()); |
|
|
|
publish(subtopics[MQTT_RSSI], String(WiFi.RSSI()).c_str()); |
|
|
|
publish(subtopics[MQTT_FREE_HEAP], String(ESP.getFreeHeap()).c_str()); |
|
|
|
#ifndef ESP32 |
|
|
@ -143,18 +147,17 @@ class PubMqtt { |
|
|
|
publish(subtopics[MQTT_COMM_START], String(sunrise + offsM).c_str(), true); |
|
|
|
publish(subtopics[MQTT_COMM_STOP], String(sunset + offsE).c_str(), true); |
|
|
|
|
|
|
|
Inverter<> *iv; |
|
|
|
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i++) { |
|
|
|
iv = mSys->getInverterByPos(i); |
|
|
|
Inverter<> *iv = mSys->getInverterByPos(i); |
|
|
|
if(NULL == iv) |
|
|
|
continue; |
|
|
|
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/dis_night_comm", iv->config->name); |
|
|
|
publish(mSubTopic, ((iv->commEnabled) ? dict[STR_TRUE] : dict[STR_FALSE]), true); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/dis_night_comm", iv->config->name); |
|
|
|
publish(mSubTopic.data(), ((iv->commEnabled) ? dict[STR_TRUE] : dict[STR_FALSE]), true); |
|
|
|
} |
|
|
|
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "comm_disabled"); |
|
|
|
publish(mSubTopic, (((*mUtcTimestamp > (sunset + offsE)) || (*mUtcTimestamp < (sunrise + offsM))) ? dict[STR_TRUE] : dict[STR_FALSE]), true); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "comm_disabled"); |
|
|
|
publish(mSubTopic.data(), (((*mUtcTimestamp > (sunset + offsE)) || (*mUtcTimestamp < (sunrise + offsM))) ? dict[STR_TRUE] : dict[STR_FALSE]), true); |
|
|
|
|
|
|
|
return true; |
|
|
|
} |
|
|
@ -176,9 +179,9 @@ class PubMqtt { |
|
|
|
|
|
|
|
void tickerMidnight() { |
|
|
|
// set Total YieldDay to zero
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "total/%s", fields[FLD_YD]); |
|
|
|
snprintf(mVal, 2, "0"); |
|
|
|
publish(mSubTopic, mVal, true); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "total/%s", fields[FLD_YD]); |
|
|
|
snprintf(mVal.data(), mVal.size(), "0"); |
|
|
|
publish(mSubTopic.data(), mVal.data(), true); |
|
|
|
} |
|
|
|
|
|
|
|
void payloadEventListener(uint8_t cmd, Inverter<> *iv) { |
|
|
@ -197,11 +200,11 @@ class PubMqtt { |
|
|
|
return; |
|
|
|
|
|
|
|
if(addTopic) |
|
|
|
snprintf(mTopic, MQTT_TOPIC_LEN + 32 + MAX_NAME_LENGTH + 1, "%s/%s", mCfgMqtt->topic, subTopic); |
|
|
|
snprintf(mTopic.data(), mTopic.size(), "%s/%s", mCfgMqtt->topic, subTopic); |
|
|
|
else |
|
|
|
snprintf(mTopic, MQTT_TOPIC_LEN + 32 + MAX_NAME_LENGTH + 1, "%s", subTopic); |
|
|
|
snprintf(mTopic.data(), mTopic.size(), "%s", subTopic); |
|
|
|
|
|
|
|
mClient.publish(mTopic, qos, retained, payload); |
|
|
|
mClient.publish(mTopic.data(), qos, retained, payload); |
|
|
|
yield(); |
|
|
|
mTxCnt++; |
|
|
|
} |
|
|
@ -238,8 +241,8 @@ class PubMqtt { |
|
|
|
|
|
|
|
void setPowerLimitAck(Inverter<> *iv) { |
|
|
|
if (NULL != iv) { |
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/%s", iv->config->name, subtopics[MQTT_ACK_PWR_LMT]); |
|
|
|
publish(mSubTopic, "true", true, true, QOS_2); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/%s", iv->config->name, subtopics[MQTT_ACK_PWR_LMT]); |
|
|
|
publish(mSubTopic.data(), "true", true, true, QOS_2); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
@ -255,15 +258,15 @@ class PubMqtt { |
|
|
|
publish(subtopics[MQTT_IP_ADDR], WiFi.localIP().toString().c_str(), true); |
|
|
|
#endif |
|
|
|
tickerMinute(); |
|
|
|
publish(mLwtTopic, mqttStr[MQTT_STR_LWT_CONN], true, false); |
|
|
|
publish(mLwtTopic.data(), mqttStr[MQTT_STR_LWT_CONN], true, false); |
|
|
|
|
|
|
|
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i++) { |
|
|
|
snprintf(mVal, 20, "ctrl/limit/%d", i); |
|
|
|
subscribe(mVal, QOS_2); |
|
|
|
snprintf(mVal, 20, "ctrl/restart/%d", i); |
|
|
|
subscribe(mVal); |
|
|
|
snprintf(mVal, 20, "ctrl/power/%d", i); |
|
|
|
subscribe(mVal); |
|
|
|
snprintf(mVal.data(), mVal.size(), "ctrl/limit/%d", i); |
|
|
|
subscribe(mVal.data(), QOS_2); |
|
|
|
snprintf(mVal.data(), mVal.size(), "ctrl/restart/%d", i); |
|
|
|
subscribe(mVal.data()); |
|
|
|
snprintf(mVal.data(), mVal.size(), "ctrl/power/%d", i); |
|
|
|
subscribe(mVal.data()); |
|
|
|
} |
|
|
|
subscribe(subscr[MQTT_SUBS_SET_TIME]); |
|
|
|
} |
|
|
@ -359,11 +362,9 @@ class PubMqtt { |
|
|
|
} |
|
|
|
|
|
|
|
void discoveryConfigLoop(void) { |
|
|
|
char topic[64], name[32], uniq_id[32], buf[350]; |
|
|
|
DynamicJsonDocument doc(256); |
|
|
|
|
|
|
|
uint8_t fldTotal[4] = {FLD_PAC, FLD_YT, FLD_YD, FLD_PDC}; |
|
|
|
const char* unitTotal[4] = {"W", "kWh", "Wh", "W"}; |
|
|
|
constexpr static uint8_t fldTotal[] = {FLD_PAC, FLD_YT, FLD_YD, FLD_PDC}; |
|
|
|
|
|
|
|
String node_id = String(mDevName) + "_TOTAL"; |
|
|
|
bool total = (mDiscovery.lastIvId == MAX_NUM_INVERTERS); |
|
|
@ -392,32 +393,37 @@ class PubMqtt { |
|
|
|
doc[F("mf")] = F("Hoymiles"); |
|
|
|
JsonObject deviceObj = doc.as<JsonObject>(); // deviceObj is only pointer!?
|
|
|
|
|
|
|
|
std::array<char, 64> topic; |
|
|
|
std::array<char, 32> name; |
|
|
|
std::array<char, 32> uniq_id; |
|
|
|
std::array<char, 350> buf; |
|
|
|
const char *devCls, *stateCls; |
|
|
|
if (!total) { |
|
|
|
if (rec->assign[mDiscovery.sub].ch == CH0) |
|
|
|
snprintf(name, 32, "%s", iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(name.data(), name.size(), "%s", iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
else |
|
|
|
snprintf(name, 32, "CH%d_%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(topic, 64, "/ch%d/%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(uniq_id, 32, "ch%d_%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(name.data(), name.size(), "CH%d_%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(topic.data(), name.size(), "/ch%d/%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(uniq_id.data(), uniq_id.size(), "ch%d_%s", rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
|
|
|
|
devCls = getFieldDeviceClass(rec->assign[mDiscovery.sub].fieldId); |
|
|
|
stateCls = getFieldStateClass(rec->assign[mDiscovery.sub].fieldId); |
|
|
|
} |
|
|
|
|
|
|
|
else { // total values
|
|
|
|
snprintf(name, 32, "Total %s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(topic, 64, "/%s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(uniq_id, 32, "total_%s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(name.data(), name.size(), "Total %s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(topic.data(), topic.size(), "/%s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(uniq_id.data(), uniq_id.size(), "total_%s", fields[fldTotal[mDiscovery.sub]]); |
|
|
|
devCls = getFieldDeviceClass(fldTotal[mDiscovery.sub]); |
|
|
|
stateCls = getFieldStateClass(fldTotal[mDiscovery.sub]); |
|
|
|
} |
|
|
|
|
|
|
|
DynamicJsonDocument doc2(512); |
|
|
|
constexpr static char* unitTotal[] = {"W", "kWh", "Wh", "W"}; |
|
|
|
doc2[F("name")] = name; |
|
|
|
doc2[F("stat_t")] = String(mCfgMqtt->topic) + "/" + ((!total) ? String(iv->config->name) : "total" ) + String(topic); |
|
|
|
doc2[F("stat_t")] = String(mCfgMqtt->topic) + "/" + ((!total) ? String(iv->config->name) : "total" ) + String(topic.data()); |
|
|
|
doc2[F("unit_of_meas")] = ((!total) ? (iv->getUnit(mDiscovery.sub, rec)) : (unitTotal[mDiscovery.sub])); |
|
|
|
doc2[F("uniq_id")] = ((!total) ? (String(iv->config->serial.u64, HEX)) : (node_id)) + "_" + uniq_id; |
|
|
|
doc2[F("uniq_id")] = ((!total) ? (String(iv->config->serial.u64, HEX)) : (node_id)) + "_" + uniq_id.data(); |
|
|
|
doc2[F("dev")] = deviceObj; |
|
|
|
if (!(String(stateCls) == String("total_increasing"))) |
|
|
|
doc2[F("exp_aft")] = MQTT_INTERVAL + 5; // add 5 sec if connection is bad or ESP too slow @TODO: stimmt das wirklich als expire!?
|
|
|
@ -427,13 +433,13 @@ class PubMqtt { |
|
|
|
doc2[F("stat_cla")] = String(stateCls); |
|
|
|
|
|
|
|
if (!total) |
|
|
|
snprintf(topic, 64, "%s/sensor/%s/ch%d_%s/config", MQTT_DISCOVERY_PREFIX, iv->config->name, rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
snprintf(topic.data(), topic.size(), "%s/sensor/%s/ch%d_%s/config", MQTT_DISCOVERY_PREFIX, iv->config->name, rec->assign[mDiscovery.sub].ch, iv->getFieldName(mDiscovery.sub, rec)); |
|
|
|
else // total values
|
|
|
|
snprintf(topic, 64, "%s/sensor/%s/total_%s/config", MQTT_DISCOVERY_PREFIX, node_id.c_str(), fields[fldTotal[mDiscovery.sub]]); |
|
|
|
snprintf(topic.data(), topic.size(), "%s/sensor/%s/total_%s/config", MQTT_DISCOVERY_PREFIX, node_id.c_str(), fields[fldTotal[mDiscovery.sub]]); |
|
|
|
size_t size = measureJson(doc2) + 1; |
|
|
|
memset(buf, 0, size); |
|
|
|
serializeJson(doc2, buf, size); |
|
|
|
publish(topic, buf, true, false); |
|
|
|
buf.fill(0); |
|
|
|
serializeJson(doc2, buf.data(), size); |
|
|
|
publish(topic.data(), buf.data(), true, false); |
|
|
|
|
|
|
|
if(++mDiscovery.sub == ((!total) ? (rec->length) : 4)) { |
|
|
|
mDiscovery.sub = 0; |
|
|
@ -503,15 +509,15 @@ class PubMqtt { |
|
|
|
mLastIvState[id] = status; |
|
|
|
changed = true; |
|
|
|
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/available", iv->config->name); |
|
|
|
snprintf(mVal, 40, "%d", (uint8_t)status); |
|
|
|
publish(mSubTopic, mVal, true); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/available", iv->config->name); |
|
|
|
snprintf(mVal.data(), mVal.size(), "%d", (uint8_t)status); |
|
|
|
publish(mSubTopic.data(), mVal.data(), true); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
if(changed) { |
|
|
|
snprintf(mVal, 32, "%d", ((allAvail) ? MQTT_STATUS_ONLINE : ((anyAvail) ? MQTT_STATUS_PARTIAL : MQTT_STATUS_OFFLINE))); |
|
|
|
publish("status", mVal, true); |
|
|
|
snprintf(mVal.data(), mVal.size(), "%d", ((allAvail) ? MQTT_STATUS_ONLINE : ((anyAvail) ? MQTT_STATUS_PARTIAL : MQTT_STATUS_OFFLINE))); |
|
|
|
publish("status", mVal.data(), true); |
|
|
|
} |
|
|
|
|
|
|
|
return anyAvail; |
|
|
@ -533,19 +539,19 @@ class PubMqtt { |
|
|
|
|
|
|
|
mSendAlarm[i] = false; |
|
|
|
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/alarm/cnt", iv->config->name); |
|
|
|
snprintf(mVal, 40, "%d", iv->alarmCnt); |
|
|
|
publish(mSubTopic, mVal, false); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/alarm/cnt", iv->config->name); |
|
|
|
snprintf(mVal.data(), mVal.size(), "%d", iv->alarmCnt); |
|
|
|
publish(mSubTopic.data(), mVal.data(), false); |
|
|
|
|
|
|
|
for(uint8_t j = 0; j < 10; j++) { |
|
|
|
if(0 != iv->lastAlarm[j].code) { |
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/alarm/%d", iv->config->name, j); |
|
|
|
snprintf(mVal, 100, "{\"code\":%d,\"str\":\"%s\",\"start\":%d,\"end\":%d}", |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/alarm/%d", iv->config->name, j); |
|
|
|
snprintf(mVal.data(), mVal.size(), "{\"code\":%d,\"str\":\"%s\",\"start\":%d,\"end\":%d}", |
|
|
|
iv->lastAlarm[j].code, |
|
|
|
iv->getAlarmStr(iv->lastAlarm[j].code).c_str(), |
|
|
|
iv->lastAlarm[j].start + lastMidnight, |
|
|
|
iv->lastAlarm[j].end + lastMidnight); |
|
|
|
publish(mSubTopic, mVal, false); |
|
|
|
publish(mSubTopic.data(), mVal.data(), false); |
|
|
|
yield(); |
|
|
|
} |
|
|
|
} |
|
|
@ -575,9 +581,9 @@ class PubMqtt { |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
snprintf(mSubTopic, 32 + MAX_NAME_LENGTH, "%s/ch%d/%s", iv->config->name, rec->assign[i].ch, fields[rec->assign[i].fieldId]); |
|
|
|
snprintf(mVal, 40, "%g", ah::round3(iv->getValue(i, rec))); |
|
|
|
publish(mSubTopic, mVal, retained); |
|
|
|
snprintf(mSubTopic.data(), mSubTopic.size(), "%s/ch%d/%s", iv->config->name, rec->assign[i].ch, fields[rec->assign[i].fieldId]); |
|
|
|
snprintf(mVal.data(), mVal.size(), "%g", ah::round3(iv->getValue(i, rec))); |
|
|
|
publish(mSubTopic.data(), mVal.data(), retained); |
|
|
|
|
|
|
|
yield(); |
|
|
|
} |
|
|
@ -597,33 +603,33 @@ class PubMqtt { |
|
|
|
} |
|
|
|
|
|
|
|
espMqttClient mClient; |
|
|
|
cfgMqtt_t *mCfgMqtt; |
|
|
|
cfgMqtt_t *mCfgMqtt = nullptr; |
|
|
|
#if defined(ESP8266) |
|
|
|
WiFiEventHandler mHWifiCon, mHWifiDiscon; |
|
|
|
#endif |
|
|
|
|
|
|
|
HMSYSTEM *mSys; |
|
|
|
HMSYSTEM *mSys = nullptr; |
|
|
|
PubMqttIvData<HMSYSTEM> mSendIvData; |
|
|
|
|
|
|
|
uint32_t *mUtcTimestamp, *mUptime; |
|
|
|
uint32_t mRxCnt, mTxCnt; |
|
|
|
uint32_t *mUtcTimestamp = nullptr, *mUptime = nullptr; |
|
|
|
uint32_t mRxCnt = 0, mTxCnt = 0; |
|
|
|
std::queue<sendListCmdIv> mSendList; |
|
|
|
std::array<bool, MAX_NUM_INVERTERS> mSendAlarm{}; |
|
|
|
subscriptionCb mSubscriptionCb; |
|
|
|
bool mLastAnyAvail; |
|
|
|
InverterStatus mLastIvState[MAX_NUM_INVERTERS]; |
|
|
|
uint32_t mIvLastRTRpub[MAX_NUM_INVERTERS]; |
|
|
|
uint16_t mIntervalTimeout; |
|
|
|
std::array<bool, MAX_NUM_INVERTERS> mSendAlarm; |
|
|
|
subscriptionCb mSubscriptionCb = nullptr; |
|
|
|
bool mLastAnyAvail = false; |
|
|
|
std::array<InverterStatus, MAX_NUM_INVERTERS> mLastIvState; |
|
|
|
std::array<uint32_t, MAX_NUM_INVERTERS> mIvLastRTRpub; |
|
|
|
uint16_t mIntervalTimeout = 0; |
|
|
|
|
|
|
|
// last will topic and payload must be available through lifetime of 'espMqttClient'
|
|
|
|
char mLwtTopic[MQTT_TOPIC_LEN+5]; |
|
|
|
const char *mDevName, *mVersion; |
|
|
|
char mClientId[24]; // number of chars is limited to 23 up to v3.1 of MQTT
|
|
|
|
std::array<char, (MQTT_TOPIC_LEN + 5)> mLwtTopic; |
|
|
|
const char *mDevName = nullptr, *mVersion = nullptr; |
|
|
|
std::array<char, 24> mClientId; // number of chars is limited to 23 up to v3.1 of MQTT
|
|
|
|
// global buffer for mqtt topic. Used when publishing mqtt messages.
|
|
|
|
char mTopic[MQTT_TOPIC_LEN + 32 + MAX_NAME_LENGTH + 1]; |
|
|
|
char mSubTopic[32 + MAX_NAME_LENGTH + 1]; |
|
|
|
char mVal[100]; |
|
|
|
discovery_t mDiscovery; |
|
|
|
std::array<char, (MQTT_TOPIC_LEN + 32 + MAX_NAME_LENGTH + 1)> mTopic; |
|
|
|
std::array<char, (32 + MAX_NAME_LENGTH + 1)> mSubTopic; |
|
|
|
std::array<char, 100> mVal; |
|
|
|
discovery_t mDiscovery = {true, 0, 0, 0}; |
|
|
|
}; |
|
|
|
|
|
|
|
#endif /*ENABLE_MQTT*/ |
|
|
|