From b201c3d93c42e4dc3339b87e17410c10693c330b Mon Sep 17 00:00:00 2001 From: Juliusz Chroboczek Date: Sat, 25 Apr 2020 22:44:24 +0200 Subject: [PATCH] Implement ping/pong exchanges and client timeouts. --- client.go | 23 +++++++++++++++++++++++ static/sfu.js | 8 ++++++++ 2 files changed, 31 insertions(+) diff --git a/client.go b/client.go index 4de2d43..e71a660 100644 --- a/client.go +++ b/client.go @@ -707,8 +707,12 @@ func clientLoop(c *client, conn *websocket.Conn) error { } } + readTime := time.Now() + ticker := time.NewTicker(2 * time.Second) defer ticker.Stop() + slowTicker := time.NewTicker(10 * time.Second) + defer slowTicker.Stop() for { select { @@ -718,6 +722,7 @@ func clientLoop(c *client, conn *websocket.Conn) error { } switch m := m.(type) { case clientMessage: + readTime = time.Now() err := handleClientMessage(c, m) if err != nil { return err @@ -793,6 +798,18 @@ func clientLoop(c *client, conn *websocket.Conn) error { } case <-ticker.C: sendRateUpdate(c) + case <-slowTicker.C: + if time.Since(readTime) > 90*time.Second { + return errors.New("client is dead") + } + if time.Since(readTime) > 60*time.Second { + err := c.write(clientMessage{ + Type: "ping", + }) + if err != nil { + return err + } + } } } } @@ -856,6 +873,12 @@ func handleClientMessage(c *client, m clientMessage) error { if err != nil { return c.error(err) } + case "pong": + // nothing + case "ping": + c.write(clientMessage{ + Type: "pong", + }) default: log.Printf("unexpected message: %v", m.Type) return protocolError("unexpected message") diff --git a/static/sfu.js b/static/sfu.js index 5ff7457..3bbf6c1 100644 --- a/static/sfu.js +++ b/static/sfu.js @@ -338,6 +338,14 @@ function serverConnect() { case 'chat': addToChatbox(m.id, m.username, m.value, m.me); break; + case 'ping': + send({ + type: 'pong', + }); + break; + case 'pong': + /* nothing */ + break; case 'error': displayError(m.value); break;