me-no-dev / ESPAsyncWebServer

Async Web Server for ESP8266 and ESP32
3.77k stars 1.22k forks source link

how to use the keepAlivePeriod for clients ? #1157

Open guestisp opened 2 years ago

guestisp commented 2 years ago

I'm trying to find a way to automatically ping all connected clients by using the native ping/pong feature (as workaround i could send custom messages from the client to the server)

I've set this in wsOnEvent:

  if (type == WS_EVT_CONNECT)
  {
    // client connected
    client->printf("Hello Client %u :)", client->id());
    client->ping();
    client->keepAlivePeriod(10);
  }
  else if (type == WS_EVT_PONG)
  {
    // pong message was received (in response to a ping request maybe)
    Serial.printf("ws[%s][%u] pong[%u]: %s\n", server->url(), client->id(), len, (len) ? (char *)data : "");
  }

and i'm expecting a ping/pong every 10 seconds, but nothing happens.

How should I enable the ping/pong ?

stale[bot] commented 2 years ago

[STALE_SET] This issue has been automatically marked as stale because it has not had recent activity. It will be closed in 14 days if no further activity occurs. Thank you for your contributions.

simonttp78 commented 2 years ago

I have same issue. Trying to find a way to close web socket client when client IP address is not responding to pings (client disconnected). keepAlivePeriod seems to be perfect solution, but it doesn't work. Any other way to close web socket for client that doesn't respond to pings?

stale[bot] commented 2 years ago

[STALE_CLR] This issue has been removed from the stale queue. Please ensure activity to keep it openin the future.

stale[bot] commented 1 year ago

[STALE_SET] This issue has been automatically marked as stale because it has not had recent activity. It will be closed in 14 days if no further activity occurs. Thank you for your contributions.

microfoundry commented 2 months ago

I had the same question and did some debugging. In the function:

void AsyncWebSocketClient::_onData(void* pbuf, size_t plen) {
...
      } else if (_pinfo.opcode == WS_PONG) {
        if (datalen != AWSC_PING_PAYLOAD_LEN || memcmp(AWSC_PING_PAYLOAD, data, AWSC_PING_PAYLOAD_LEN) != 0) {
          _server->_handleEvent(this, WS_EVT_PONG, NULL, data, datalen);
        }
...   

The received data will only be queued as a WS_EVT_PONG IF the WS_PONG data IS NOT the default "ESPAsyncWebServer-PING" that is transmitted via the keepAlivePeriod() value. In my case, via wireshark (and additional Serial debugging added to, but omitted from the original code above), I see the PONG response is the same, hence no Event is queued to handle...

If the desire is to send all PONG responses to the event handler, comment out/remove the if() statement...

void AsyncWebSocketClient::_onData(void* pbuf, size_t plen) {
...
      } else if (_pinfo.opcode == WS_PONG) {
        // if (datalen != AWSC_PING_PAYLOAD_LEN || memcmp(AWSC_PING_PAYLOAD, data, AWSC_PING_PAYLOAD_LEN) != 0) {
          _server->_handleEvent(this, WS_EVT_PONG, NULL, data, datalen);
        // }
...   
stale[bot] commented 2 months ago

[STALE_CLR] This issue has been removed from the stale queue. Please ensure activity to keep it openin the future.