Compare commits

...

6 Commits

Author SHA1 Message Date
Gunnar Skjold
c74e719327 Fixed ESP8266 build issue 2024-04-13 11:38:03 +02:00
Gunnar Skjold
8c8e14f60c Some changes for cloud 2024-04-13 11:29:56 +02:00
Gunnar Skjold
3b93897a8e Added new headers to upgrade request 2024-04-13 10:19:08 +02:00
Gunnar Skjold
e080c7d535 Fixed static IP 2024-04-11 22:08:58 +02:00
Gunnar Skjold
64ea8c4888 Fixed static IP 2024-04-10 20:44:05 +02:00
Gunnar Skjold
e7ae24b26f Fixed accidental clearing more than just GPIO 2024-04-10 20:36:43 +02:00
8 changed files with 94 additions and 28 deletions

View File

@@ -295,7 +295,7 @@ public:
bool getGpioConfig(GpioConfig&); bool getGpioConfig(GpioConfig&);
bool setGpioConfig(GpioConfig&); bool setGpioConfig(GpioConfig&);
void clearGpio(GpioConfig&); void clearGpio(GpioConfig& config, bool all=true);
void print(Print* debugger); void print(Print* debugger);

View File

@@ -518,7 +518,7 @@ bool AmsConfiguration::setGpioConfig(GpioConfig& config) {
return ret; return ret;
} }
void AmsConfiguration::clearGpio(GpioConfig& config) { void AmsConfiguration::clearGpio(GpioConfig& config, bool all) {
config.apPin = 0xFF; config.apPin = 0xFF;
config.ledPin = 0xFF; config.ledPin = 0xFF;
config.ledInverted = true; config.ledInverted = true;
@@ -529,13 +529,16 @@ void AmsConfiguration::clearGpio(GpioConfig& config) {
config.tempSensorPin = 0xFF; config.tempSensorPin = 0xFF;
config.tempAnalogSensorPin = 0xFF; config.tempAnalogSensorPin = 0xFF;
config.vccPin = 0xFF; config.vccPin = 0xFF;
config.vccOffset = 0;
config.vccMultiplier = 1000;
config.vccBootLimit = 0;
config.vccResistorGnd = 0;
config.vccResistorVcc = 0;
config.ledDisablePin = 0xFF; config.ledDisablePin = 0xFF;
config.ledBehaviour = LED_BEHAVIOUR_DEFAULT;
if(all) {
config.vccOffset = 0;
config.vccMultiplier = 1000;
config.vccBootLimit = 0;
config.vccResistorGnd = 0;
config.vccResistorVcc = 0;
config.ledBehaviour = LED_BEHAVIOUR_DEFAULT;
}
} }
bool AmsConfiguration::getNtpConfig(NtpConfig& config) { bool AmsConfiguration::getNtpConfig(NtpConfig& config) {

View File

@@ -42,7 +42,7 @@ static const char CC_JSON_POWER_LIST3[] PROGMEM = ",\"%s\":{\"P\":%lu,\"Q\":%lu,
static const char CC_JSON_PHASE[] PROGMEM = "%s\"%d\":{\"u\":%.2f,\"i\":%s}"; static const char CC_JSON_PHASE[] PROGMEM = "%s\"%d\":{\"u\":%.2f,\"i\":%s}";
static const char CC_JSON_PHASE_LIST4[] PROGMEM = "%s\"%d\":{\"u\":%.2f,\"i\":%s,\"Pim\":%lu,\"Pex\":%lu,\"pf\":%.2f}"; static const char CC_JSON_PHASE_LIST4[] PROGMEM = "%s\"%d\":{\"u\":%.2f,\"i\":%s,\"Pim\":%lu,\"Pex\":%lu,\"pf\":%.2f}";
static const char CC_JSON_STATUS[] PROGMEM = ",\"status\":{\"esp\":{\"state\":%d,\"error\":%d},\"han\":{\"state\":%d,\"error\":%d},\"wifi\":{\"state\":%d,\"error\":%d},\"mqtt\":{\"state\":%d,\"error\":%d}}"; static const char CC_JSON_STATUS[] PROGMEM = ",\"status\":{\"esp\":{\"state\":%d,\"error\":%d},\"han\":{\"state\":%d,\"error\":%d},\"wifi\":{\"state\":%d,\"error\":%d},\"mqtt\":{\"state\":%d,\"error\":%d}}";
static const char CC_JSON_INIT[] PROGMEM = ",\"init\":{\"mac\":\"%s\",\"apmac\":\"%s\",\"version\":\"%s\",\"boardType\":%d,\"bootReason\":%d,\"bootCause\":%d,\"utcOffset\":%d},\"meter\":{\"manufacturerId\":%d,\"manufacturer\":\"%s\",\"model\":\"%s\",\"id\":\"%s\",\"system\":\"%s\",\"fuse\":%d,\"import\":%d,\"export\":%d},\"network\":{\"ip\":\"%s\",\"mask\":\"%s\",\"gw\":\"%s\",\"dns1\":\"%s\",\"dns2\":\"%s\"}"; static const char CC_JSON_INIT[] PROGMEM = ",\"init\":{\"mac\":\"%s\",\"apmac\":\"%s\",\"version\":\"%s\",\"boardType\":%d,\"bootReason\":%d,\"bootCause\":%d,\"tz\":\"%s\"},\"meter\":{\"manufacturerId\":%d,\"manufacturer\":\"%s\",\"model\":\"%s\",\"id\":\"%s\",\"system\":\"%s\",\"fuse\":%d,\"import\":%d,\"export\":%d},\"network\":{\"ip\":\"%s\",\"mask\":\"%s\",\"gw\":\"%s\",\"dns1\":\"%s\",\"dns2\":\"%s\"}";
struct CloudData { struct CloudData {
uint8_t type; uint8_t type;
@@ -52,11 +52,12 @@ struct CloudData {
class CloudConnector { class CloudConnector {
public: public:
CloudConnector(RemoteDebug*); CloudConnector(RemoteDebug*);
bool setup(CloudConfig& config, MeterConfig& meter, SystemConfig& system, HwTools* hw, ResetDataContainer* rdc); bool setup(CloudConfig& config, MeterConfig& meter, SystemConfig& system, NtpConfig& ntp, HwTools* hw, ResetDataContainer* rdc);
void setMqttHandler(AmsMqttHandler* mqttHandler); void setMqttHandler(AmsMqttHandler* mqttHandler);
void update(AmsData& data, EnergyAccounting& ea); void update(AmsData& data, EnergyAccounting& ea);
void setPriceConfig(PriceServiceConfig&);
void setEnergyAccountingConfig(EnergyAccountingConfig&);
void forceUpdate(); void forceUpdate();
void setTimezone(Timezone* tz);
void setConnectionHandler(ConnectionHandler* ch); void setConnectionHandler(ConnectionHandler* ch);
private: private:
@@ -64,13 +65,17 @@ private:
HwTools* hw = NULL; HwTools* hw = NULL;
ConnectionHandler* ch = NULL; ConnectionHandler* ch = NULL;
ResetDataContainer* rdc = NULL; ResetDataContainer* rdc = NULL;
Timezone* tz = NULL;
AmsMqttHandler* mqttHandler = NULL; AmsMqttHandler* mqttHandler = NULL;
CloudConfig config; CloudConfig config;
PriceServiceConfig priceConfig;
unsigned long lastPriceConfig = 0;
EnergyAccountingConfig eac;
unsigned long lastEac = 0;
HTTPClient http; HTTPClient http;
WiFiUDP udp; WiFiUDP udp;
int maxPwr = 0; int maxPwr = 0;
uint8_t boardType = 0; uint8_t boardType = 0;
char timezone[32];
uint8_t distributionSystem = 0; uint8_t distributionSystem = 0;
uint16_t mainFuse = 0, productionCapacity = 0; uint16_t mainFuse = 0, productionCapacity = 0;

View File

@@ -46,7 +46,7 @@ CloudConnector::CloudConnector(RemoteDebug* debugger) {
sprintf_P(this->apmac, PSTR("%02X:%02X:%02X:%02X:%02X:%02X"), apmac[0], apmac[1], apmac[2], apmac[3], apmac[4], apmac[5]); sprintf_P(this->apmac, PSTR("%02X:%02X:%02X:%02X:%02X:%02X"), apmac[0], apmac[1], apmac[2], apmac[3], apmac[4], apmac[5]);
} }
bool CloudConnector::setup(CloudConfig& config, MeterConfig& meter, SystemConfig& system, HwTools* hw, ResetDataContainer* rdc) { bool CloudConnector::setup(CloudConfig& config, MeterConfig& meter, SystemConfig& system, NtpConfig& ntp, HwTools* hw, ResetDataContainer* rdc) {
bool ret = false; bool ret = false;
#if defined(ESP32) #if defined(ESP32)
if(!ESPRandom::isValidV4Uuid(config.clientId)) { if(!ESPRandom::isValidV4Uuid(config.clientId)) {
@@ -61,6 +61,7 @@ bool CloudConnector::setup(CloudConfig& config, MeterConfig& meter, SystemConfig
this->rdc = rdc; this->rdc = rdc;
this->boardType = system.boardType; this->boardType = system.boardType;
strcpy(this->timezone, ntp.timezone);
this->maxPwr = 0; this->maxPwr = 0;
this->distributionSystem = meter.distributionSystem; this->distributionSystem = meter.distributionSystem;
@@ -204,7 +205,7 @@ void CloudConnector::update(AmsData& data, EnergyAccounting& ea) {
boardType, boardType,
rtc_get_reset_reason(0), rtc_get_reset_reason(0),
rdc == NULL ? 0 : rdc->last_cause, rdc == NULL ? 0 : rdc->last_cause,
tz == NULL ? 0 : (tz->toLocal(now)-now)/3600, timezone,
data.getMeterType(), data.getMeterType(),
meterManufacturer(data.getMeterType()).c_str(), meterManufacturer(data.getMeterType()).c_str(),
data.getMeterModel().c_str(), data.getMeterModel().c_str(),
@@ -219,6 +220,23 @@ void CloudConnector::update(AmsData& data, EnergyAccounting& ea) {
dns1.toString().c_str(), dns1.toString().c_str(),
dns2.toString().c_str() dns2.toString().c_str()
); );
} else if(lastPriceConfig == 0) {
pos += snprintf_P(clearBuffer+pos, CC_BUF_SIZE-pos, PSTR(",\"price\":{\"area\":\"%s\",\"currency\":\"%s\"}"), priceConfig.area, priceConfig.currency);
lastPriceConfig = now;
} else if(lastEac == 0) {
pos += snprintf_P(clearBuffer+pos, CC_BUF_SIZE-pos, PSTR(",\"accounting\":{\"hours\":%d,\"thresholds\":[%d,%d,%d,%d,%d,%d,%d,%d,%d]}"),
eac.hours,
eac.thresholds[0],
eac.thresholds[1],
eac.thresholds[2],
eac.thresholds[3],
eac.thresholds[4],
eac.thresholds[5],
eac.thresholds[6],
eac.thresholds[7],
eac.thresholds[8]
);
lastEac = now;
} }
float vcc = 0.0; float vcc = 0.0;
@@ -382,16 +400,24 @@ void CloudConnector::update(AmsData& data, EnergyAccounting& ea) {
void CloudConnector::forceUpdate() { void CloudConnector::forceUpdate() {
lastUpdate = 0; lastUpdate = 0;
} lastPriceConfig = 0;
lastEac = 0;
void CloudConnector::setTimezone(Timezone* tz) {
this->tz = tz;
} }
void CloudConnector::setConnectionHandler(ConnectionHandler* ch) { void CloudConnector::setConnectionHandler(ConnectionHandler* ch) {
this->ch = ch; this->ch = ch;
} }
void CloudConnector::setPriceConfig(PriceServiceConfig& priceConfig) {
this->priceConfig = priceConfig;
this->lastPriceConfig = 0;
}
void CloudConnector::setEnergyAccountingConfig(EnergyAccountingConfig& eac) {
this->eac = eac;
this->lastEac = 0;
}
void CloudConnector::debugPrint(byte *buffer, int start, int length) { void CloudConnector::debugPrint(byte *buffer, int start, int length) {
for (int i = start; i < start + length; i++) { for (int i = start; i < start + length; i++) {
if (buffer[i] < 0x10) if (buffer[i] < 0x10)

View File

@@ -90,6 +90,7 @@ bool WiFiClientConnectionHandler::connect(NetworkConfig config, SystemConfig sys
} }
#endif #endif
WiFi.setAutoReconnect(true); WiFi.setAutoReconnect(true);
this->config = config;
#if defined(ESP32) #if defined(ESP32)
if(begin(config.ssid, config.psk)) { if(begin(config.ssid, config.psk)) {
#else #else
@@ -112,7 +113,6 @@ bool WiFiClientConnectionHandler::connect(NetworkConfig config, SystemConfig sys
} else { } else {
if (debugger->isActive(RemoteDebug::ERROR)) debugger->printf_P(PSTR("Unable to start WiFi\n")); if (debugger->isActive(RemoteDebug::ERROR)) debugger->printf_P(PSTR("Unable to start WiFi\n"));
} }
this->config = config;
return true; return true;
} }
return false; return false;
@@ -164,7 +164,7 @@ wl_status_t WiFiClientConnectionHandler::begin(const char* ssid, const char* pas
} }
} }
if(strlen(config.ip) > 0){ if(strlen(config.ip) == 0){
if(set_esp_interface_ip(ESP_IF_WIFI_STA) != ESP_OK) { if(set_esp_interface_ip(ESP_IF_WIFI_STA) != ESP_OK) {
return WL_CONNECT_FAILED; return WL_CONNECT_FAILED;
} }

View File

@@ -142,6 +142,8 @@ private:
void redirectToMain(); void redirectToMain();
void robotstxt(); void robotstxt();
void ssdpSchema(); void ssdpSchema();
void updaterRequestCallback(HTTPClient*);
}; };
#endif #endif

View File

@@ -1652,7 +1652,11 @@ void AmsWebServer::upgradeFromUrl(String url, String nextVersion) {
httpUpdate.rebootOnUpdate(false); httpUpdate.rebootOnUpdate(false);
httpUpdate.setFollowRedirects(HTTPC_STRICT_FOLLOW_REDIRECTS); httpUpdate.setFollowRedirects(HTTPC_STRICT_FOLLOW_REDIRECTS);
#if defined(ESP32)
HTTPUpdateResult ret = httpUpdate.update(client, url, currentVersion, std::bind(&AmsWebServer::updaterRequestCallback, this, std::placeholders::_1));
#else
HTTPUpdateResult ret = httpUpdate.update(client, url, currentVersion); HTTPUpdateResult ret = httpUpdate.update(client, url, currentVersion);
#endif
int lastError = httpUpdate.getLastError(); int lastError = httpUpdate.getLastError();
config->setUpgradeInformation(ret, ret == HTTP_UPDATE_OK ? 0 : lastError, FirmwareVersion::VersionString, nextVersion.c_str()); config->setUpgradeInformation(ret, ret == HTTP_UPDATE_OK ? 0 : lastError, FirmwareVersion::VersionString, nextVersion.c_str());
@@ -1672,6 +1676,19 @@ void AmsWebServer::upgradeFromUrl(String url, String nextVersion) {
} }
} }
void AmsWebServer::updaterRequestCallback(HTTPClient* http) {
SystemConfig sys;
if(config->getSystemConfig(sys)) {
http->addHeader(F("x-AMS-board-type"), String(sys.boardType, 10));
if(meterState->getMeterType() != AmsTypeAutodetect) {
http->addHeader(F("x-AMS-meter-mfg"), String(meterState->getMeterType(), 10));
}
if(!meterState->getMeterModel().isEmpty()) {
http->addHeader(F("x-AMS-meter-model"), meterState->getMeterModel());
}
}
}
void AmsWebServer::firmwareHtml() { void AmsWebServer::firmwareHtml() {
if(!checkSecurity(1)) if(!checkSecurity(1))
return; return;

View File

@@ -280,7 +280,7 @@ void setup() {
if(config.getSystemConfig(sysConfig)) { if(config.getSystemConfig(sysConfig)) {
config.getMeterConfig(meterConfig); config.getMeterConfig(meterConfig);
if(sysConfig.boardType < 20) { if(sysConfig.boardType < 20) {
config.clearGpio(gpioConfig); config.clearGpio(gpioConfig, false);
hw.applyBoardConfig(sysConfig.boardType, gpioConfig, meterConfig, meterConfig.rxPin); hw.applyBoardConfig(sysConfig.boardType, gpioConfig, meterConfig, meterConfig.rxPin);
config.setMeterConfig(meterConfig); config.setMeterConfig(meterConfig);
config.setGpioConfig(gpioConfig); config.setGpioConfig(gpioConfig);
@@ -674,11 +674,19 @@ void loop() {
if(cloud == NULL) { if(cloud == NULL) {
cloud = new CloudConnector(&Debug); cloud = new CloudConnector(&Debug);
} }
if(cloud->setup(cc, meterConfig, sysConfig, &hw, &rdc)) { NtpConfig ntp;
config.getNtpConfig(ntp);
if(cloud->setup(cc, meterConfig, sysConfig, ntp, &hw, &rdc)) {
config.setCloudConfig(cc); config.setCloudConfig(cc);
} }
cloud->setTimezone(tz);
cloud->setConnectionHandler(ch); cloud->setConnectionHandler(ch);
PriceServiceConfig price;
config.getPriceServiceConfig(price);
cloud->setPriceConfig(price);
EnergyAccountingConfig *eac = ea.getConfig();
cloud->setEnergyAccountingConfig(*eac);
} }
config.ackCloudConfig(); config.ackCloudConfig();
} }
@@ -908,6 +916,11 @@ void handleEnergyAccountingChanged() {
config.getEnergyAccountingConfig(*eac); config.getEnergyAccountingConfig(*eac);
ea.setup(&ds, eac); ea.setup(&ds, eac);
config.ackEnergyAccountingChange(); config.ackEnergyAccountingChange();
#if defined(ESP32)
if(cloud != NULL) {
cloud->setEnergyAccountingConfig(*eac);
}
#endif
} }
char ntpServerName[64] = ""; char ntpServerName[64] = "";
@@ -931,11 +944,6 @@ void handleNtpChange() {
ws.setTimezone(tz); ws.setTimezone(tz);
ds.setTimezone(tz); ds.setTimezone(tz);
ea.setTimezone(tz); ea.setTimezone(tz);
#if defined(ESP32)
if(cloud != NULL) {
cloud->setTimezone(tz);
}
#endif
} }
config.ackNtpChange(); config.ackNtpChange();
@@ -1049,6 +1057,11 @@ void handlePriceService(unsigned long now) {
ps = new PriceService(&Debug); ps = new PriceService(&Debug);
ea.setPriceService(ps); ea.setPriceService(ps);
ws.setPriceService(ps); ws.setPriceService(ps);
#if defined(ESP32)
if(cloud != NULL) {
cloud->setPriceConfig(price);
}
#endif
} }
ps->setup(price); ps->setup(price);
} else if(ps != NULL) { } else if(ps != NULL) {