Browse Source

* improved api

* finished index page
pull/283/head
lumapu 2 years ago
parent
commit
1f6db2ffdb
  1. 54
      tools/esp8266/app.cpp
  2. 7
      tools/esp8266/app.h
  3. 63
      tools/esp8266/html/index.html
  4. 8
      tools/esp8266/web.cpp
  5. 1
      tools/esp8266/web.h
  6. 76
      tools/esp8266/webApi.cpp
  7. 2
      tools/esp8266/webApi.h

54
tools/esp8266/app.cpp

@ -53,14 +53,12 @@ void app::loop(void) {
bool apActive = mWifi->loop();
mWebInst->loop();
if(checkTicker(&mUptimeTicker, mUptimeInterval)) {
if(millis() - mPrevMillis >= 1000) {
mPrevMillis += 1000;
mUptimeSecs++;
if(0 != mTimestamp)
mTimestamp++;
}
}
if(checkTicker(&mNtpRefreshTicker, mNtpRefreshInterval)) {
if(!apActive) {
@ -500,56 +498,6 @@ void app::cbMqtt(char* topic, byte* payload, unsigned int length) {
}
//-----------------------------------------------------------------------------
String app::getStatistics(void) {
String content = F("Receive success: ") + String(mStat.rxSuccess) + "\n";
content += F("Receive fail: ") + String(mStat.rxFail) + "\n";
content += F("Frames received: ") + String(mStat.frmCnt) + "\n";
content += F("Send Cnt: ") + String(mSys->Radio.mSendCnt) + String("\n\n");
Inverter<> *iv;
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i++) {
iv = mSys->getInverterByPos(i);
content += F("Inverter #") + String(i) + F(": ");
if(NULL != iv) {
bool avail = true;
content += String(iv->name) + F(" (v") + String(iv->fwVersion) +F(")") + F(" is ");
if(!iv->isAvailable(mTimestamp)) {
content += F("not ");
avail = false;
}
content += F("available and is ");
if(!iv->isProducing(mTimestamp))
content += F("not ");
content += F("producing\n");
if(!avail) {
if(iv->getLastTs() > 0)
content += F("-> last successful transmission: ") + getDateTimeStr(iv->getLastTs()) + "\n";
}
}
else
content += F("n/a\n");
}
if(!mSys->Radio.isChipConnected())
content += F("WARNING! your NRF24 module can't be reached, check the wiring and pinout (<a href=\"/setup\">setup</a>)\n");
if(mShowRebootRequest)
content += F("INFO: reboot your ESP to apply all your configuration changes!\n");
if(!mSettingsValid)
content += F("INFO: your settings are invalid, please switch to <a href=\"/setup\">Setup</a> to correct this.\n");
content += F("MQTT: ");
if(!mMqtt.isConnected())
content += F("not ");
content += F("connected\n");
return content;
}
//-----------------------------------------------------------------------------
String app::getJson(void) {
DPRINTLN(DBG_VERBOSE, F("app::showJson"));
@ -664,8 +612,6 @@ const char* app::getFieldStateClass(uint8_t fieldId) {
//-----------------------------------------------------------------------------
void app::resetSystem(void) {
mUptimeSecs = 0;
mUptimeTicker = 0xffffffff;
mUptimeInterval = 500; // [ms]
mPrevMillis = 0;
mNtpRefreshTicker = 0;

7
tools/esp8266/app.h

@ -62,7 +62,6 @@ class app {
void cbMqtt(char* topic, byte* payload, unsigned int length);
void saveValues(void);
void resetPayload(Inverter<>* iv);
String getStatistics(void);
String getJson(void);
bool getWifiApActive(void);
@ -135,6 +134,10 @@ class app {
return false;
}
inline bool mqttIsConnected(void) { return mMqtt.isConnected(); }
inline bool getSettingsValid(void) { return mSettingsValid; }
inline bool getRebootRequestState(void) { return mShowRebootRequest; }
HmSystemType *mSys;
bool mShouldReboot;
@ -214,8 +217,6 @@ class app {
}
uint32_t mUptimeTicker;
uint16_t mUptimeInterval;
uint32_t mUptimeSecs;
uint32_t mPrevMillis;
uint8_t mHeapStatCnt;

63
tools/esp8266/html/index.html

@ -15,8 +15,14 @@
<a href="/setup">Setup</a><br/>
</p>
<p><span class="des">Uptime: </span><span id="uptime"></span></p>
<p><span class="des">Statistics: </span><pre id="stat"></pre></p>
<p>Every {TS}seconds the values are updated</p>
<p><span class="des">ESP-Time: </span><span id="date"></span></p>
<p>
<span class="des">Statistics: </span>
<pre id="stat"></pre>
<pre id="iv"></pre>
<pre id="warn_info"></pre>
</p>
<p>Every <span id="refresh"></span> seconds the values are updated</p>
<div id="note">
This project was started from <a href="https://www.mikrocontroller.net/topic/525778" target="_blank">this discussion. (Mikrocontroller.net)</a><br/>
@ -35,8 +41,10 @@
<p class="left"><a href="/update">Update Firmware</a></p>
<p class="right" id="version"></p>
<p class="right"><a href="/reboot">Reboot</a></p>
<p class="right"><a href="/api">REST API</a></p>
</div>
<script type="text/javascript">
var intervalSet = false;
function parseSys(obj) {
document.getElementById("version").innerHTML = "Git SHA: " + obj["build"] + " :: " + obj["version"];
@ -49,10 +57,8 @@
document.getElementById("uptime").innerHTML = days + " Days, "
+ ("0"+hrs).substr(-2) + ":"
+ ("0"+min).substr(-2) + ":"
+ ("0"+sec).substr(-2) + "; now: "
+ ("0"+date.getHours()).substr(-2) + ":"
+ ("0"+date.getMinutes()).substr(-2) + ":"
+ ("0"+date.getSeconds()).substr(-2);
+ ("0"+sec).substr(-2);
document.getElementById("date").innerHTML = date.toLocaleString('de-DE', {timeZone: 'UTC'});
}
function parseStat(obj) {
@ -62,11 +68,48 @@
+ "\nTX Cnt: " + obj["tx_cnt"];
}
window.setInterval("getAjax('/api/system', parseSys)", 30000);
window.setInterval("getAjax('/api/statistics', parseStat)", 30000);
function parseIv(obj) {
var html = "";
for(var i of obj) {
html += "Inverter #" + i["id"] + ": " + i["name"] + " (v" + i["version"] + ") is ";
if(false == i["is_avail"])
html += "not ";
html += "available and is ";
if(false == i["is_producing"])
html += "not ";
html += "producing\n";
if(false == i["is_avail"]) {
var date = new Date(i["ts_last_succes"] * 1000);
html += "-> last successful transmission: " + date.toLocaleString('de-DE', {timeZone: 'UTC'});
}
}
document.getElementById("iv").innerHTML = html;
}
function parseWarnInfo(warn, info) {
var html = "";
for(var w of warn) {
html += "WARN: " + w + "\n";
}
for(var i of info) {
html += "INFO: " + i + "\n";
}
document.getElementById("warn_info").innerHTML = html;
}
function parse(obj) {
parseSys(obj["system"]);
parseStat(obj["statistics"]);
parseIv(obj["inverter"]);
parseWarnInfo(obj["warnings"], obj["infos"]);
document.getElementById("refresh").innerHTML = obj["refresh_interval"];
if(false == intervalSet)
window.setInterval("getAjax('/api/index', parse)", obj["refresh_interval"] * 1000);
}
getAjax("/api/system", parseSys);
getAjax("/api/statistics", parseStat);
getAjax("/api/index", parse);
</script>
</body>
</html>

8
tools/esp8266/web.cpp

@ -51,7 +51,6 @@ void web::setup(void) {
mWeb->on("/setup", HTTP_GET, std::bind(&web::onSetup, this, std::placeholders::_1));
mWeb->on("/save", HTTP_ANY, std::bind(&web::showSave, this, std::placeholders::_1));
mWeb->on("/cmdstat", HTTP_ANY, std::bind(&web::showStatistics, this, std::placeholders::_1));
mWeb->on("/visualization", HTTP_ANY, std::bind(&web::showVisualization, this, std::placeholders::_1));
mWeb->on("/livedata", HTTP_ANY, std::bind(&web::showLiveData, this, std::placeholders::_1));
mWeb->on("/json", HTTP_ANY, std::bind(&web::showJson, this, std::placeholders::_1));
@ -319,13 +318,6 @@ void web::showSave(AsyncWebServerRequest *request) {
}
//-----------------------------------------------------------------------------
void web::showStatistics(AsyncWebServerRequest *request) {
DPRINTLN(DBG_VERBOSE, F("web::showStatistics"));
request->send(200, F("text/plain"), mMain->getStatistics());
}
//-----------------------------------------------------------------------------
void web::showVisualization(AsyncWebServerRequest *request) {
DPRINTLN(DBG_VERBOSE, F("web::showVisualization"));

1
tools/esp8266/web.h

@ -37,7 +37,6 @@ class web {
void onSetup(AsyncWebServerRequest *request);
void showSave(AsyncWebServerRequest *request);
void showStatistics(AsyncWebServerRequest *request);
void showVisualization(AsyncWebServerRequest *request);
void showLiveData(AsyncWebServerRequest *request);
void showJson(AsyncWebServerRequest *request);

76
tools/esp8266/webApi.cpp

@ -46,13 +46,14 @@ void webApi::onApi(AsyncWebServerRequest *request) {
else if(path == "pinout") getPinout(root);
else if(path == "radio") getRadio(root);
else if(path == "serial") getSerial(root);
else if(path == "index") getIndex(root);
else if(path == "setup") getSetup(root);
else
root["info"] = "not found"; //root["url"] = request->url();
getNotFound(root, F("http://") + request->host() + F("/api/"));
response->setLength();
//response->addHeader("Access-Control-Allow-Origin", "*");
//response->addHeader("Access-Control-Allow-Headers", "content-type");
response->addHeader("Access-Control-Allow-Origin", "*");
response->addHeader("Access-Control-Allow-Headers", "content-type");
request->send(response);
}
@ -79,7 +80,7 @@ void webApi::getStatistics(JsonObject obj) {
//-----------------------------------------------------------------------------
void webApi::getInverterList(JsonObject obj) {
JsonArray invArr = obj.createNestedArray("inverter");
JsonArray invArr = obj.createNestedArray(F("inverter"));
Inverter<> *iv;
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i ++) {
@ -146,13 +147,66 @@ void webApi::getSerial(JsonObject obj) {
}
//-----------------------------------------------------------------------------
void webApi::getNotFound(JsonObject obj, String url) {
JsonObject ep = obj.createNestedObject("avail_endpoints");
ep[F("system")] = url + F("system");
ep[F("statistics")] = url + F("statistics");
ep[F("inverter/list")] = url + F("inverter/list");
ep[F("mqtt")] = url + F("mqtt");
ep[F("ntp")] = url + F("ntp");
ep[F("pinout")] = url + F("pinout");
ep[F("radio")] = url + F("radio");
ep[F("serial")] = url + F("serial");
ep[F("index")] = url + F("index");
ep[F("setup")] = url + F("setup");
}
//-----------------------------------------------------------------------------
void webApi::getIndex(JsonObject obj) {
getSystem(obj.createNestedObject(F("system")));
getStatistics(obj.createNestedObject(F("statistics")));
obj["refresh_interval"] = SEND_INTERVAL;
JsonArray inv = obj.createNestedArray(F("inverter"));
Inverter<> *iv;
for(uint8_t i = 0; i < MAX_NUM_INVERTERS; i ++) {
iv = mApp->mSys->getInverterByPos(i);
if(NULL != iv) {
JsonObject invObj = inv.createNestedObject();
invObj[F("id")] = i;
invObj[F("name")] = String(iv->name);
invObj[F("version")] = String(iv->fwVersion);
invObj[F("is_avail")] = iv->isAvailable(mApp->getTimestamp());
invObj[F("is_producing")] = iv->isProducing(mApp->getTimestamp());
invObj[F("ts_last_success")] = iv->getLastTs();
}
}
JsonArray warn = obj.createNestedArray(F("warnings"));
if(!mApp->mSys->Radio.isChipConnected())
warn.add(F("your NRF24 module can't be reached, check the wiring and pinout"));
if(!mApp->mqttIsConnected())
warn.add(F("MQTT is not connected"));
JsonArray info = obj.createNestedArray(F("infos"));
if(mApp->getRebootRequestState())
info.add(F("reboot your ESP to apply all your configuration changes!"));
if(!mApp->getSettingsValid())
info.add(F("your settings are invalid"));
if(mApp->mqttIsConnected())
info.add(F("MQTT is connected"));
}
//-----------------------------------------------------------------------------
void webApi::getSetup(JsonObject obj) {
getSystem(obj.createNestedObject("system"));
getInverterList(obj.createNestedObject("inverter"));
getMqtt(obj.createNestedObject("mqtt"));
getNtp(obj.createNestedObject("ntp"));
getPinout(obj.createNestedObject("pinout"));
getRadio(obj.createNestedObject("radio"));
getSerial(obj.createNestedObject("serial"));
getSystem(obj.createNestedObject(F("system")));
getInverterList(obj.createNestedObject(F("inverter")));
getMqtt(obj.createNestedObject(F("mqtt")));
getNtp(obj.createNestedObject(F("ntp")));
getPinout(obj.createNestedObject(F("pinout")));
getRadio(obj.createNestedObject(F("radio")));
getSerial(obj.createNestedObject(F("serial")));
}

2
tools/esp8266/webApi.h

@ -29,6 +29,8 @@ class webApi {
void getRadio(JsonObject obj);
void getSerial(JsonObject obj);
void getNotFound(JsonObject obj, String url);
void getIndex(JsonObject obj);
void getSetup(JsonObject obj);
AsyncWebServer *mSrv;

Loading…
Cancel
Save