Handle multiple display connections

Also drop the `quit` channel as we get good-enough signaling by closing the data channel.
This commit is contained in:
Vojtěch Káně
2026-10-05 10:16:48 +02:00
parent 19cc468f83
commit e3602ac25e
+40 -11
View File
@@ -6,6 +6,7 @@ import (
"log" "log"
"net/http" "net/http"
"os" "os"
"sync"
"github.com/gorilla/websocket" "github.com/gorilla/websocket"
) )
@@ -18,8 +19,19 @@ var upgrader = websocket.Upgrader{
}, },
} }
type client struct {
nudges chan [2]int
quit chan bool
}
type clientsStore struct {
set map[*client]struct{}
sync.RWMutex
}
func main() { func main() {
var nudges = make(chan [2]int) var clients clientsStore
clients.set = make(map[*client]struct{})
go func() { go func() {
mux := http.NewServeMux() mux := http.NewServeMux()
@@ -45,7 +57,17 @@ func main() {
w.WriteHeader(http.StatusBadRequest) w.WriteHeader(http.StatusBadRequest)
return return
} }
nudges <- nudge (func() {
clients.RLock()
defer clients.RUnlock()
for c, _ := range clients.set {
select {
case c.nudges <- nudge:
default:
log.Println("Client too slow -> dropping nudge")
}
}
})()
w.WriteHeader(http.StatusNoContent) w.WriteHeader(http.StatusNoContent)
case "GET": case "GET":
w.Header().Add("Content-Type", "text/html") w.Header().Add("Content-Type", "text/html")
@@ -82,24 +104,31 @@ func main() {
log.Println(err) log.Println(err)
return return
} }
var quit = make(chan bool) defer con.Close()
var c client
c.nudges = make(chan [2]int)
(func() {
clients.Lock()
defer clients.Unlock()
clients.set[&c] = struct{}{}
})()
defer (func() {
clients.Lock()
defer clients.Unlock()
delete(clients.set, &c)
log.Println("Closing client connection")
})()
con.SetCloseHandler(func(code int, text string) error { con.SetCloseHandler(func(code int, text string) error {
quit <- true close(c.nudges)
return nil return nil
}) })
for { for n := range c.nudges {
select {
case <-quit:
return
case n := <-nudges:
log.Println(n)
err := con.WriteJSON(n) err := con.WriteJSON(n)
if err != nil { if err != nil {
log.Println(err) log.Println(err)
return return
} }
} }
}
}) })
log.Println(http.ListenAndServe(":8081", mux)) log.Println(http.ListenAndServe(":8081", mux))
} }