Eventsource golang: how to detect client disconnection?

I'm developing Twitter hashtag chats with events sent by the server with the https://github.com/antage/eventsource package

I have a problem disconnecting the client. I run the program to send messages to the client, but when the client disconnects, the program still works.

I do not know how to detect on the server side that the client is disconnected.

func (sh StreamHandler) ServeHTTP(resp http.ResponseWriter, req *http.Request) { es := eventsource.New( &eventsource.Settings{ Timeout: 2 * time.Second, CloseOnTimeout: true, IdleTimeout: 2 * time.Second, Gzip: true, }, func(req *http.Request) [][]byte { return [][]byte{ []byte("X-Accel-Buffering: no"), []byte("Access-Control-Allow-Origin: *"), } }, ) es.ServeHTTP(resp, req) go func() { var id int for { id++ time.Sleep(1 * time.Second) es.SendEventMessage("blabla", "message", strconv.Itoa(id)) } }() } 
+9
source share
3 answers

You can use CloseNotifier, which tells you if the main http connection is closed . Like:

 notify := w.(http.CloseNotifier).CloseNotify() go func() { <-notify // connection close, do cleanup, etc. }() 

NTN

+5
source

You can check ConsumersCount() :

  go func() { var id int for es.ConsumersCount() > 0 { id++ es.SendEventMessage("blabla", "message", strconv.Itoa(id)) time.Sleep(1 * time.Second) } fmt.Println("closed") }() 

A kind of hack, but it seems to work.

You may be better off using another package or making your own so that you can better control the lifetime of your goroutines. You may find a closed connection on .Write (which this package does not open).

If you need an example chat server in TCP: chat-server . And a video tutorial to go with it: a tutorial .

The same basic template should work for SSE.

+3
source

As of December 2018, obviously, CloseNotifier is out of date . The recommended solution is to use the Request context. The following worked for me:

 done := make(chan bool) go func() { <-req.Context().Done() done <- true }() <-done 
+1
source

All Articles