Add Adaptive Polling Intervals to WebServer (#7864)
Some checks are pending
CI / setup (check) (push) Waiting to run
CI / setup (esp32) (push) Waiting to run
CI / setup (esp32c3) (push) Waiting to run
CI / setup (esp32c6) (push) Waiting to run
CI / setup (esp32s3) (push) Waiting to run
CI / setup (nrf52840) (push) Waiting to run
CI / setup (rp2040) (push) Waiting to run
CI / setup (rp2350) (push) Waiting to run
CI / setup (stm32) (push) Waiting to run
CI / version (push) Waiting to run
CI / check (push) Blocked by required conditions
CI / build-esp32 (push) Blocked by required conditions
CI / build-esp32s3 (push) Blocked by required conditions
CI / build-esp32c3 (push) Blocked by required conditions
CI / build-esp32c6 (push) Blocked by required conditions
CI / build-nrf52840 (push) Blocked by required conditions
CI / build-rp2040 (push) Blocked by required conditions
CI / build-rp2350 (push) Blocked by required conditions
CI / build-stm32 (push) Blocked by required conditions
CI / build-debian-src (push) Waiting to run
CI / package-pio-deps-native-tft (push) Waiting to run
CI / test-native (push) Waiting to run
CI / docker-deb-amd64 (push) Waiting to run
CI / docker-deb-amd64-tft (push) Waiting to run
CI / docker-alp-amd64 (push) Waiting to run
CI / docker-alp-amd64-tft (push) Waiting to run
CI / docker-deb-arm64 (push) Waiting to run
CI / docker-deb-armv7 (push) Waiting to run
CI / gather-artifacts (esp32) (push) Blocked by required conditions
CI / gather-artifacts (esp32c3) (push) Blocked by required conditions
CI / gather-artifacts (esp32c6) (push) Blocked by required conditions
CI / gather-artifacts (esp32s3) (push) Blocked by required conditions
CI / gather-artifacts (nrf52840) (push) Blocked by required conditions
CI / gather-artifacts (rp2040) (push) Blocked by required conditions
CI / gather-artifacts (rp2350) (push) Blocked by required conditions
CI / gather-artifacts (stm32) (push) Blocked by required conditions
CI / release-artifacts (push) Blocked by required conditions
CI / release-firmware (esp32) (push) Blocked by required conditions
CI / release-firmware (esp32c3) (push) Blocked by required conditions
CI / release-firmware (esp32c6) (push) Blocked by required conditions
CI / release-firmware (esp32s3) (push) Blocked by required conditions
CI / release-firmware (nrf52840) (push) Blocked by required conditions
CI / release-firmware (rp2040) (push) Blocked by required conditions
CI / release-firmware (rp2350) (push) Blocked by required conditions
CI / release-firmware (stm32) (push) Blocked by required conditions
CI / publish-firmware (push) Blocked by required conditions

* feat: add adaptive polling intervals to WebServer

Replace fixed 5ms polling with adaptive intervals based on HTTP activity:
- 50ms during active periods (first 5 seconds after request)
- 200ms during medium activity (5-30 seconds)
- 1000ms during idle periods (30+ seconds)

Reduces CPU usage significantly during idle periods while maintaining
responsiveness when handling HTTP requests.

* Fix integer overflow and magic numbers in WebServer

- Handle millis() overflow in getAdaptiveInterval()
- Replace magic numbers with named constants
- Improve code readability and maintainability
This commit is contained in:
Dmitry Dubinin 2025-10-06 13:52:40 +03:00 committed by GitHub
parent 18ca9e80d5
commit 29f4d99bf6
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 42 additions and 2 deletions

View File

@ -148,6 +148,8 @@ void registerHandlers(HTTPServer *insecureServer, HTTPSServer *secureServer)
void handleAPIv1FromRadio(HTTPRequest *req, HTTPResponse *res) void handleAPIv1FromRadio(HTTPRequest *req, HTTPResponse *res)
{ {
if (webServerThread)
webServerThread->markActivity();
LOG_DEBUG("webAPI handleAPIv1FromRadio"); LOG_DEBUG("webAPI handleAPIv1FromRadio");
@ -391,6 +393,9 @@ void handleFsDeleteStatic(HTTPRequest *req, HTTPResponse *res)
void handleStatic(HTTPRequest *req, HTTPResponse *res) void handleStatic(HTTPRequest *req, HTTPResponse *res)
{ {
if (webServerThread)
webServerThread->markActivity();
// Get access to the parameters // Get access to the parameters
ResourceParameters *params = req->getParams(); ResourceParameters *params = req->getParams();

View File

@ -49,6 +49,12 @@ Preferences prefs;
using namespace httpsserver; using namespace httpsserver;
#include "mesh/http/ContentHandler.h" #include "mesh/http/ContentHandler.h"
static const uint32_t ACTIVE_THRESHOLD_MS = 5000;
static const uint32_t MEDIUM_THRESHOLD_MS = 30000;
static const int32_t ACTIVE_INTERVAL_MS = 50;
static const int32_t MEDIUM_INTERVAL_MS = 200;
static const int32_t IDLE_INTERVAL_MS = 1000;
static SSLCert *cert; static SSLCert *cert;
static HTTPSServer *secureServer; static HTTPSServer *secureServer;
static HTTPServer *insecureServer; static HTTPServer *insecureServer;
@ -175,6 +181,32 @@ WebServerThread::WebServerThread() : concurrency::OSThread("WebServer")
if (!config.network.wifi_enabled && !config.network.eth_enabled) { if (!config.network.wifi_enabled && !config.network.eth_enabled) {
disable(); disable();
} }
lastActivityTime = millis();
}
void WebServerThread::markActivity()
{
lastActivityTime = millis();
}
int32_t WebServerThread::getAdaptiveInterval()
{
uint32_t currentTime = millis();
uint32_t timeSinceActivity;
if (currentTime >= lastActivityTime) {
timeSinceActivity = currentTime - lastActivityTime;
} else {
timeSinceActivity = (UINT32_MAX - lastActivityTime) + currentTime + 1;
}
if (timeSinceActivity < ACTIVE_THRESHOLD_MS) {
return ACTIVE_INTERVAL_MS;
} else if (timeSinceActivity < MEDIUM_THRESHOLD_MS) {
return MEDIUM_INTERVAL_MS;
} else {
return IDLE_INTERVAL_MS;
}
} }
int32_t WebServerThread::runOnce() int32_t WebServerThread::runOnce()
@ -189,8 +221,7 @@ int32_t WebServerThread::runOnce()
ESP.restart(); ESP.restart();
} }
// Loop every 5ms. return getAdaptiveInterval();
return (5);
} }
void initWebServer() void initWebServer()

View File

@ -10,13 +10,17 @@ void createSSLCert();
class WebServerThread : private concurrency::OSThread class WebServerThread : private concurrency::OSThread
{ {
private:
uint32_t lastActivityTime = 0;
public: public:
WebServerThread(); WebServerThread();
uint32_t requestRestart = 0; uint32_t requestRestart = 0;
void markActivity();
protected: protected:
virtual int32_t runOnce() override; virtual int32_t runOnce() override;
int32_t getAdaptiveInterval();
}; };
extern WebServerThread *webServerThread; extern WebServerThread *webServerThread;