Extended configuration to allow string names
* Current config will be migrated to new format * Already extended web API to get/post new format
This commit is contained in:
parent
0c46ecf121
commit
d28fadbdac
@ -4,7 +4,7 @@
|
||||
#include <Arduino.h>
|
||||
|
||||
#define CONFIG_FILENAME "/config.json"
|
||||
#define CONFIG_VERSION 0x00011600 // 0.1.22 // make sure to clean all after change
|
||||
#define CONFIG_VERSION 0x00011700 // 0.1.23 // make sure to clean all after change
|
||||
|
||||
#define WIFI_MAX_SSID_STRLEN 31
|
||||
#define WIFI_MAX_PASSWORD_STRLEN 64
|
||||
@ -25,12 +25,19 @@
|
||||
#define INV_MAX_COUNT 10
|
||||
#define INV_MAX_CHAN_COUNT 4
|
||||
|
||||
#define CHAN_MAX_NAME_STRLEN 31
|
||||
|
||||
#define JSON_BUFFER_SIZE 6144
|
||||
|
||||
struct CHANNEL_CONFIG_T {
|
||||
uint16_t MaxChannelPower;
|
||||
char Name[CHAN_MAX_NAME_STRLEN];
|
||||
};
|
||||
|
||||
struct INVERTER_CONFIG_T {
|
||||
uint64_t Serial;
|
||||
char Name[INV_MAX_NAME_STRLEN + 1];
|
||||
uint16_t MaxChannelPower[INV_MAX_CHAN_COUNT];
|
||||
CHANNEL_CONFIG_T channel[INV_MAX_CHAN_COUNT];
|
||||
};
|
||||
|
||||
struct CONFIG_T {
|
||||
|
||||
@ -84,9 +84,11 @@ bool ConfigurationClass::write()
|
||||
inv["serial"] = config.Inverter[i].Serial;
|
||||
inv["name"] = config.Inverter[i].Name;
|
||||
|
||||
JsonArray channels = inv.createNestedArray("channels");
|
||||
JsonArray channel = inv.createNestedArray("channel");
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
channels.add(config.Inverter[i].MaxChannelPower[c]);
|
||||
JsonObject chanData = channel.createNestedObject();
|
||||
chanData["name"] = config.Inverter[i].channel[c].Name;
|
||||
chanData["max_power"] = config.Inverter[i].channel[c].MaxChannelPower;
|
||||
}
|
||||
}
|
||||
|
||||
@ -202,9 +204,10 @@ bool ConfigurationClass::read()
|
||||
config.Inverter[i].Serial = inv["serial"] | 0ULL;
|
||||
strlcpy(config.Inverter[i].Name, inv["name"] | "", sizeof(config.Inverter[i].Name));
|
||||
|
||||
JsonArray channels = inv["channels"];
|
||||
JsonArray channel = inv["channel"];
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
config.Inverter[i].MaxChannelPower[c] = channels[c];
|
||||
config.Inverter[i].channel[c].MaxChannelPower = channel[c]["max_power"] | 0;
|
||||
strlcpy(config.Inverter[i].channel[c].Name, channel[c]["name"] | "", sizeof(config.Inverter[i].channel[c].Name));
|
||||
}
|
||||
}
|
||||
|
||||
@ -214,8 +217,35 @@ bool ConfigurationClass::read()
|
||||
|
||||
void ConfigurationClass::migrate()
|
||||
{
|
||||
if (config.Cfg_Version < 0x00011700) {
|
||||
File f = LittleFS.open(CONFIG_FILENAME, "r", false);
|
||||
if (!f) {
|
||||
Serial.println(F("Failed to open file, cancel migration"));
|
||||
return;
|
||||
}
|
||||
|
||||
DynamicJsonDocument doc(JSON_BUFFER_SIZE);
|
||||
// Deserialize the JSON document
|
||||
DeserializationError error = deserializeJson(doc, f);
|
||||
if (error) {
|
||||
Serial.println(F("Failed to read file, cancel migration"));
|
||||
return;
|
||||
}
|
||||
|
||||
JsonArray inverters = doc["inverters"];
|
||||
for (uint8_t i = 0; i < INV_MAX_COUNT; i++) {
|
||||
JsonObject inv = inverters[i].as<JsonObject>();
|
||||
JsonArray channels = inv["channels"];
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
config.Inverter[i].channel[c].MaxChannelPower = channels[c];
|
||||
strlcpy(config.Inverter[i].channel[c].Name, "", sizeof(config.Inverter[i].channel[c].Name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
config.Cfg_Version = CONFIG_VERSION;
|
||||
write();
|
||||
read();
|
||||
}
|
||||
|
||||
CONFIG_T& ConfigurationClass::get()
|
||||
|
||||
@ -62,8 +62,11 @@ void WebApiInverterClass::onInverterList(AsyncWebServerRequest* request)
|
||||
max_channels = inv->Statistics()->getChannelCount();
|
||||
}
|
||||
|
||||
JsonArray channel = obj.createNestedArray("channel");
|
||||
for (uint8_t c = 0; c < max_channels; c++) {
|
||||
obj[F("max_power")][c] = config.Inverter[i].MaxChannelPower[c];
|
||||
JsonObject chanData = channel.createNestedObject();
|
||||
chanData["name"] = config.Inverter[i].channel[c].Name;
|
||||
chanData["max_power"] = config.Inverter[i].channel[c].MaxChannelPower;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -154,7 +157,7 @@ void WebApiInverterClass::onInverterAdd(AsyncWebServerRequest* request)
|
||||
|
||||
if (inv != nullptr) {
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
inv->Statistics()->setChannelMaxPower(c, inverter->MaxChannelPower[c]);
|
||||
inv->Statistics()->setChannelMaxPower(c, inverter->channel[c].MaxChannelPower);
|
||||
}
|
||||
}
|
||||
|
||||
@ -197,7 +200,7 @@ void WebApiInverterClass::onInverterEdit(AsyncWebServerRequest* request)
|
||||
return;
|
||||
}
|
||||
|
||||
if (!(root.containsKey("id") && root.containsKey("serial") && root.containsKey("name") && root.containsKey("max_power"))) {
|
||||
if (!(root.containsKey("id") && root.containsKey("serial") && root.containsKey("name") && root.containsKey("channel"))) {
|
||||
retMsg[F("message")] = F("Values are missing!");
|
||||
response->setLength();
|
||||
request->send(response);
|
||||
@ -225,8 +228,8 @@ void WebApiInverterClass::onInverterEdit(AsyncWebServerRequest* request)
|
||||
return;
|
||||
}
|
||||
|
||||
JsonArray maxPowerArray = root[F("max_power")].as<JsonArray>();
|
||||
if (maxPowerArray.size() == 0 || maxPowerArray.size() > INV_MAX_CHAN_COUNT) {
|
||||
JsonArray channelArray = root[F("channel")].as<JsonArray>();
|
||||
if (channelArray.size() == 0 || channelArray.size() > INV_MAX_CHAN_COUNT) {
|
||||
retMsg[F("message")] = F("Invalid amount of max channel setting given!");
|
||||
response->setLength();
|
||||
request->send(response);
|
||||
@ -243,8 +246,9 @@ void WebApiInverterClass::onInverterEdit(AsyncWebServerRequest* request)
|
||||
strncpy(inverter.Name, root[F("name")].as<String>().c_str(), INV_MAX_NAME_STRLEN);
|
||||
|
||||
uint8_t arrayCount = 0;
|
||||
for (JsonVariant maxPower : maxPowerArray) {
|
||||
inverter.MaxChannelPower[arrayCount] = maxPower.as<uint16_t>();
|
||||
for (JsonVariant channel : channelArray) {
|
||||
inverter.channel[arrayCount].MaxChannelPower = channel[F("max_power")].as<uint16_t>();
|
||||
strncpy(inverter.channel[arrayCount].Name, channel[F("name")] | "", sizeof(inverter.channel[arrayCount].Name));
|
||||
arrayCount++;
|
||||
}
|
||||
|
||||
@ -272,7 +276,7 @@ void WebApiInverterClass::onInverterEdit(AsyncWebServerRequest* request)
|
||||
|
||||
if (inv != nullptr) {
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
inv->Statistics()->setChannelMaxPower(c, inverter.MaxChannelPower[c]);
|
||||
inv->Statistics()->setChannelMaxPower(c, inverter.channel[c].MaxChannelPower);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -116,7 +116,7 @@ void setup()
|
||||
|
||||
if (inv != nullptr) {
|
||||
for (uint8_t c = 0; c < INV_MAX_CHAN_COUNT; c++) {
|
||||
inv->Statistics()->setChannelMaxPower(c, config.Inverter[i].MaxChannelPower[c]);
|
||||
inv->Statistics()->setChannelMaxPower(c, config.Inverter[i].channel[c].MaxChannelPower);
|
||||
}
|
||||
}
|
||||
Serial.println(F(" done"));
|
||||
|
||||
@ -81,12 +81,12 @@
|
||||
class="form-control" maxlength="31" />
|
||||
</div>
|
||||
|
||||
<div v-for="(max, index) in selectedInverterData.max_power" :key="`${index}`">
|
||||
<div v-for="(max, index) in selectedInverterData.channel" :key="`${index}`">
|
||||
<label :for="`inverter-max_${index}`" class="col-form-label">Max power string {{ index +1 }}:</label>
|
||||
<div class="d-flex mb-2">
|
||||
<div class="input-group">
|
||||
<input type="number" class="form-control" :id="`inverter-max_${index}`" min="0"
|
||||
v-model="selectedInverterData.max_power[index]"
|
||||
v-model="selectedInverterData.channel[index].max_power"
|
||||
:aria-describedby="`inverter-maxDescription_${index} inverter-customizer`" />
|
||||
<span class="input-group-text" :id="`inverter-maxDescription_${index}`">W<sup>*</sup></span>
|
||||
</div>
|
||||
@ -139,12 +139,17 @@ import * as bootstrap from 'bootstrap';
|
||||
import BootstrapAlert from "@/components/BootstrapAlert.vue";
|
||||
import { handleResponse, authHeader } from '@/utils/authentication';
|
||||
|
||||
declare interface Channel {
|
||||
name: string;
|
||||
max_power: number;
|
||||
}
|
||||
|
||||
declare interface Inverter {
|
||||
id: string;
|
||||
serial: number;
|
||||
name: string;
|
||||
type: string;
|
||||
max_power: number[];
|
||||
channel: Array<Channel>;
|
||||
}
|
||||
|
||||
declare interface AlertResponse {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user