60
60
#include < pgmspace.h>
61
61
62
62
// increment on change
63
- #define SOFTWARE_VERSION_STR " NRZ-2020-131 "
63
+ #define SOFTWARE_VERSION_STR " NRZ-2020-133 "
64
64
String SOFTWARE_VERSION (SOFTWARE_VERSION_STR);
65
65
66
66
/* ****************************************************************
@@ -347,6 +347,10 @@ unsigned long min_micro = 1000000000;
347
347
unsigned long max_micro = 0 ;
348
348
349
349
bool is_SDS_running = true ;
350
+ enum {
351
+ SDS_REPLY_HDR = 10 ,
352
+ SDS_REPLY_BODY = 8
353
+ } SDS_waiting_for;
350
354
bool is_PMS_running = true ;
351
355
bool is_HPM_running = true ;
352
356
bool is_NPM_running = true ;
@@ -466,6 +470,7 @@ double last_value_GPS_lon = -200.0;
466
470
String last_value_GPS_timestamp;
467
471
String last_data_string;
468
472
int last_signal_strength;
473
+ int last_disconnect_reason;
469
474
470
475
String esp_chipid;
471
476
String esp_mac_id;
@@ -634,18 +639,18 @@ static void readConfig(bool oldconfig = false) {
634
639
continue ;
635
640
}
636
641
switch (c.cfg_type ) {
637
- case Config_Type_Bool:
638
- *(c.cfg_val .as_bool ) = boolFromJSON (json, c.cfg_key ());
639
- break ;
640
- case Config_Type_UInt:
641
- case Config_Type_Time:
642
- *(c.cfg_val .as_uint ) = json[c.cfg_key ()].as <unsigned int >();
643
- break ;
644
- case Config_Type_String:
645
- case Config_Type_Password:
646
- strncpy (c.cfg_val .as_str , json[c.cfg_key ()].as <char *>(), c.cfg_len );
647
- c.cfg_val .as_str [c.cfg_len ] = ' \0 ' ;
648
- break ;
642
+ case Config_Type_Bool:
643
+ *(c.cfg_val .as_bool ) = boolFromJSON (json, c.cfg_key ());
644
+ break ;
645
+ case Config_Type_UInt:
646
+ case Config_Type_Time:
647
+ *(c.cfg_val .as_uint ) = json[c.cfg_key ()].as <unsigned int >();
648
+ break ;
649
+ case Config_Type_String:
650
+ case Config_Type_Password:
651
+ strncpy (c.cfg_val .as_str , json[c.cfg_key ()].as <char *>(), c.cfg_len );
652
+ c.cfg_val .as_str [c.cfg_len ] = ' \0 ' ;
653
+ break ;
649
654
};
650
655
}
651
656
String writtenVersion (json[" SOFTWARE_VERSION" ].as <char *>());
@@ -1588,7 +1593,13 @@ static void webserver_status() {
1588
1593
1589
1594
page_content += FPSTR (EMPTY_ROW);
1590
1595
page_content += F (" <tr><td colspan='2'><b>" INTL_ERROR " </b></td></tr>" );
1591
- add_table_row_from_value (page_content, F (" WiFi" ), String (WiFi_error_count));
1596
+ String wifiStatus (WiFi_error_count);
1597
+ wifiStatus += ' /' ;
1598
+ wifiStatus += String (last_signal_strength);
1599
+ wifiStatus += ' /' ;
1600
+ wifiStatus += String (last_disconnect_reason);
1601
+ add_table_row_from_value (page_content, F (" WiFi" ), wifiStatus);
1602
+
1592
1603
if (last_update_returncode != 0 ) {
1593
1604
add_table_row_from_value (page_content, F (" OTA Return" ),
1594
1605
last_update_returncode > 0 ? String (last_update_returncode) : HTTPClient::errorToString (last_update_returncode));
@@ -1783,7 +1794,6 @@ static void webserver_data_json() {
1783
1794
age = 0 - age;
1784
1795
} else {
1785
1796
s1 = last_data_string;
1786
- debug_outln (last_data_string, DEBUG_MED_INFO);
1787
1797
age = msSince (starttime);
1788
1798
if (age > cfg::sending_intervall_ms) {
1789
1799
age = 0 ;
@@ -1797,19 +1807,19 @@ static void webserver_data_json() {
1797
1807
}
1798
1808
1799
1809
/* ****************************************************************
1800
- * Webserver prometheus metrics endpoint *
1810
+ * Webserver metrics endpoint *
1801
1811
*****************************************************************/
1802
- static void webserver_prometheus_endpoint () {
1803
- debug_outln_info (F (" ws: prometheus endpoint... " ));
1804
- String page_content = F ( " software_version{version= \" " SOFTWARE_VERSION_STR " \" ,{id}} 1 \n uptime_ms{{id}} {up} \n sending_intervall_ms{{id}} {si} \n number_of_measurements{{id}} {cs} \n " );
1805
- debug_outln_info ( F (" Parse JSON for Prometheus " ) );
1812
+ static void webserver_metrics_endpoint () {
1813
+ debug_outln_info (F (" ws: /metrics " ));
1814
+ RESERVE_STRING (page_content, XLARGE_STR );
1815
+ page_content = F (" software_version{version= \" " SOFTWARE_VERSION_STR " \" ,$i} 1 \n uptime_ms{$i} $u \n sending_intervall_ms{$i} $s \n number_of_measurements{$i} $c \n " );
1806
1816
String id (F (" node=\" " SENSOR_BASENAME));
1807
1817
id += esp_chipid;
1808
1818
id += ' \" ' ;
1809
- page_content.replace (" {id} " , id);
1810
- page_content.replace (" {up} " , String (msSince (time_point_device_start_ms)));
1811
- page_content.replace (" {si} " , String (cfg::sending_intervall_ms));
1812
- page_content.replace (" {cs} " , String (count_sends));
1819
+ page_content.replace (" $i " , id);
1820
+ page_content.replace (" $u " , String (msSince (time_point_device_start_ms)));
1821
+ page_content.replace (" $s " , String (cfg::sending_intervall_ms));
1822
+ page_content.replace (" $c " , String (count_sends));
1813
1823
DynamicJsonDocument json2data (JSON_BUFFER_SIZE);
1814
1824
DeserializationError err = deserializeJson (json2data, last_data_string);
1815
1825
if (!err) {
@@ -1829,13 +1839,22 @@ static void webserver_prometheus_endpoint() {
1829
1839
} else {
1830
1840
debug_outln_error (FPSTR (DBG_TXT_DATA_READ_FAILED));
1831
1841
}
1842
+ page_content += F (" # EOF\n " );
1832
1843
debug_outln (page_content, DEBUG_MED_INFO);
1833
1844
server.send (200 , FPSTR (TXT_CONTENT_TYPE_TEXT_PLAIN), page_content);
1834
1845
}
1835
1846
1836
1847
/* ****************************************************************
1837
1848
* Webserver Images *
1838
1849
*****************************************************************/
1850
+
1851
+ static void webserver_favicon () {
1852
+ server.sendHeader (F (" Cache-Control" ), F (" max-age=2592000, public" ));
1853
+
1854
+ server.send_P (200 , TXT_CONTENT_TYPE_IMAGE_PNG,
1855
+ LUFTDATEN_INFO_LOGO_PNG, LUFTDATEN_INFO_LOGO_PNG_SIZE);
1856
+ }
1857
+
1839
1858
static void webserver_static () {
1840
1859
server.sendHeader (F (" Cache-Control" ), F (" max-age=2592000, public" ));
1841
1860
@@ -1884,7 +1903,8 @@ static void setup_webserver() {
1884
1903
server.on (F (" /removeConfig" ), webserver_removeConfig);
1885
1904
server.on (F (" /reset" ), webserver_reset);
1886
1905
server.on (F (" /data.json" ), webserver_data_json);
1887
- server.on (F (" /metrics" ), webserver_prometheus_endpoint);
1906
+ server.on (F (" /metrics" ), webserver_metrics_endpoint);
1907
+ server.on (F (" /favicon.ico" ), webserver_favicon);
1888
1908
server.on (F (STATIC_PREFIX), webserver_static);
1889
1909
server.onNotFound (webserver_not_found);
1890
1910
@@ -2025,6 +2045,9 @@ static void waitForWifiToConnect(int maxRetries) {
2025
2045
/* ****************************************************************
2026
2046
* WiFi auto connecting script *
2027
2047
*****************************************************************/
2048
+
2049
+ static WiFiEventHandler disconnectEventHandler;
2050
+
2028
2051
static void connectWifi () {
2029
2052
display_debug (F (" Connecting to" ), String (cfg::wlanssid));
2030
2053
#if defined(ESP8266)
@@ -2035,6 +2058,10 @@ static void connectWifi() {
2035
2058
WiFi.setSleepMode (WIFI_NONE_SLEEP);
2036
2059
WiFi.setPhyMode (WIFI_PHY_MODE_11N);
2037
2060
delay (100 );
2061
+
2062
+ disconnectEventHandler = WiFi.onStationModeDisconnected ([](const WiFiEventStationModeDisconnected& evt) {
2063
+ last_disconnect_reason = evt.reason ;
2064
+ });
2038
2065
#endif
2039
2066
if (WiFi.getAutoConnect ()) {
2040
2067
WiFi.setAutoConnect (false );
@@ -2055,7 +2082,7 @@ static void connectWifi() {
2055
2082
#endif
2056
2083
2057
2084
WiFi.mode (WIFI_STA);
2058
-
2085
+
2059
2086
#if defined(ESP8266)
2060
2087
WiFi.hostname (cfg::fs_ssid);
2061
2088
#endif
@@ -2453,9 +2480,6 @@ static void fetchSensorDS18B20(String& s) {
2453
2480
* read SDS011 sensor values *
2454
2481
*****************************************************************/
2455
2482
static void fetchSensorSDS (String& s) {
2456
-
2457
- debug_outln_verbose (FPSTR (DBG_TXT_START_READING), FPSTR (SENSORS_SDS011));
2458
-
2459
2483
if (cfg::sending_intervall_ms > (WARMUPTIME_SDS_MS + READINGTIME_SDS_MS) &&
2460
2484
msSince (starttime) < (cfg::sending_intervall_ms - (WARMUPTIME_SDS_MS + READINGTIME_SDS_MS))) {
2461
2485
if (is_SDS_running) {
@@ -2464,27 +2488,37 @@ static void fetchSensorSDS(String& s) {
2464
2488
} else {
2465
2489
if (! is_SDS_running) {
2466
2490
is_SDS_running = SDS_cmd (PmSensorCmd::Start);
2491
+ SDS_waiting_for = SDS_REPLY_HDR;
2467
2492
}
2468
2493
2469
- const uint8_t constexpr header_measurement[2 ] = { 0xAA , 0xC0 };
2470
-
2471
- while (serialSDS.available () >= 10 &&
2472
- serialSDS.find (header_measurement, sizeof (header_measurement))) {
2494
+ while (serialSDS.available () >= SDS_waiting_for) {
2495
+ const uint8_t constexpr hdr_measurement[2 ] = { 0xAA , 0xC0 };
2473
2496
uint8_t data[8 ];
2474
- unsigned r = serialSDS.readBytes (data, sizeof (data));
2475
- if (r == sizeof (data) && SDS_checksum_valid (data)) {
2476
- uint32_t pm25_serial = data[0 ] | (data[1 ] << 8 );
2477
- uint32_t pm10_serial = data[2 ] | (data[3 ] << 8 );
2478
-
2479
- if (msSince (starttime) > (cfg::sending_intervall_ms - READINGTIME_SDS_MS)) {
2480
- sds_pm10_sum += pm10_serial;
2481
- sds_pm25_sum += pm25_serial;
2482
- UPDATE_MIN_MAX (sds_pm10_min, sds_pm10_max, pm10_serial);
2483
- UPDATE_MIN_MAX (sds_pm25_min, sds_pm25_max, pm25_serial);
2484
- debug_outln_verbose (F (" PM10 (sec.) : " ), String (pm10_serial / 10 .0f ));
2485
- debug_outln_verbose (F (" PM2.5 (sec.): " ), String (pm25_serial / 10 .0f ));
2486
- sds_val_count++;
2497
+
2498
+ switch (SDS_waiting_for) {
2499
+ case SDS_REPLY_HDR:
2500
+ if (serialSDS.find (hdr_measurement, sizeof (hdr_measurement)))
2501
+ SDS_waiting_for = SDS_REPLY_BODY;
2502
+ break ;
2503
+ case SDS_REPLY_BODY:
2504
+ debug_outln_verbose (FPSTR (DBG_TXT_START_READING), FPSTR (SENSORS_SDS011));
2505
+ if (serialSDS.readBytes (data, sizeof (data)) == sizeof (data) && SDS_checksum_valid (data)) {
2506
+ uint32_t pm25_serial = data[0 ] | (data[1 ] << 8 );
2507
+ uint32_t pm10_serial = data[2 ] | (data[3 ] << 8 );
2508
+
2509
+ if (msSince (starttime) > (cfg::sending_intervall_ms - READINGTIME_SDS_MS)) {
2510
+ sds_pm10_sum += pm10_serial;
2511
+ sds_pm25_sum += pm25_serial;
2512
+ UPDATE_MIN_MAX (sds_pm10_min, sds_pm10_max, pm10_serial);
2513
+ UPDATE_MIN_MAX (sds_pm25_min, sds_pm25_max, pm25_serial);
2514
+ debug_outln_verbose (F (" PM10 (sec.) : " ), String (pm10_serial / 10 .0f ));
2515
+ debug_outln_verbose (F (" PM2.5 (sec.): " ), String (pm25_serial / 10 .0f ));
2516
+ sds_val_count++;
2517
+ }
2487
2518
}
2519
+ debug_outln_verbose (FPSTR (DBG_TXT_END_READING), FPSTR (SENSORS_SDS011));
2520
+ SDS_waiting_for = SDS_REPLY_HDR;
2521
+ break ;
2488
2522
}
2489
2523
}
2490
2524
}
@@ -2522,8 +2556,6 @@ static void fetchSensorSDS(String& s) {
2522
2556
}
2523
2557
}
2524
2558
}
2525
-
2526
- debug_outln_verbose (FPSTR (DBG_TXT_END_READING), FPSTR (SENSORS_SDS011));
2527
2559
}
2528
2560
2529
2561
/* ****************************************************************
@@ -4195,14 +4227,17 @@ static unsigned long sendDataToOptionalApis(const String &data) {
4195
4227
4196
4228
void setup (void ) {
4197
4229
Debug.begin (9600 ); // Output to Serial at 9600 baud
4198
- #if defined(ESP8266) && !NPM_READ
4199
- serialSDS.begin (9600 , SWSERIAL_8N1, PM_SERIAL_RX, PM_SERIAL_TX);
4200
- serialSDS.enableIntTx (true );
4230
+ #if defined (ESP8266)
4231
+ serialSDS.begin (
4232
+ #if !NPM_READ
4233
+ 9600 , SWSERIAL_8N1,
4234
+ #else
4235
+ 115200 , SWSERIAL_8E1,
4201
4236
#endif
4202
- #if defined(ESP8266) && NPM_READ
4203
- serialSDS.begin (115200 , SWSERIAL_8E1, PM_SERIAL_RX, PM_SERIAL_TX);
4237
+ PM_SERIAL_RX, PM_SERIAL_TX);
4204
4238
serialSDS.enableIntTx (true );
4205
4239
#endif
4240
+
4206
4241
#if defined(ESP32) && !NPM_READ
4207
4242
serialSDS.begin (9600 , SERIAL_8N1, PM_SERIAL_RX, PM_SERIAL_TX);
4208
4243
#endif
@@ -4212,7 +4247,7 @@ void setup(void) {
4212
4247
pinMode (PIN_CS, OUTPUT);
4213
4248
digitalWrite (PIN_CS, LOW);
4214
4249
#endif
4215
- serialSDS.setTimeout ((12 * 9 * 1000 ) / 9600 );
4250
+ serialSDS.setTimeout ((4 * 12 * 1000 ) / 9600 );
4216
4251
4217
4252
#if defined(WIFI_LoRa_32_V2)
4218
4253
// reset the OLED display, e.g. of the heltec_wifi_lora_32 board
0 commit comments