Fix concurrent panic

This commit is contained in:
lesismal
2021-05-20 03:01:17 +08:00
parent 7bd65910e5
commit e21886f3a7
2 changed files with 27 additions and 24 deletions
+8 -7
View File
@@ -174,13 +174,14 @@ func (m *Melody) HandleRequestWithKeys(w http.ResponseWriter, r *http.Request, k
} }
session := &Session{ session := &Session{
Request: r, Request: r,
Keys: keys, Keys: keys,
conn: conn, conn: conn,
output: make(chan *envelope, m.Config.MessageBufferSize), output: make(chan *envelope, m.Config.MessageBufferSize),
melody: m, outputDone: make(chan struct{}),
open: true, melody: m,
rwmutex: &sync.RWMutex{}, open: true,
rwmutex: &sync.RWMutex{},
} }
m.hub.register <- session m.hub.register <- session
+19 -17
View File
@@ -11,13 +11,14 @@ import (
// Session wrapper around websocket connections. // Session wrapper around websocket connections.
type Session struct { type Session struct {
Request *http.Request Request *http.Request
Keys map[string]interface{} Keys map[string]interface{}
conn *websocket.Conn conn *websocket.Conn
output chan *envelope output chan *envelope
melody *Melody outputDone chan struct{}
open bool melody *Melody
rwmutex *sync.RWMutex open bool
rwmutex *sync.RWMutex
} }
func (s *Session) writeMessage(message *envelope) { func (s *Session) writeMessage(message *envelope) {
@@ -56,12 +57,13 @@ func (s *Session) closed() bool {
} }
func (s *Session) close() { func (s *Session) close() {
if !s.closed() { s.rwmutex.Lock()
s.rwmutex.Lock() open := s.open
s.open = false s.open = false
s.rwmutex.Unlock()
if open {
s.conn.Close() s.conn.Close()
close(s.output) close(s.outputDone)
s.rwmutex.Unlock()
} }
} }
@@ -76,11 +78,7 @@ func (s *Session) writePump() {
loop: loop:
for { for {
select { select {
case msg, ok := <-s.output: case msg := <-s.output:
if !ok {
break loop
}
err := s.writeRaw(msg) err := s.writeRaw(msg)
if err != nil { if err != nil {
@@ -101,6 +99,10 @@ loop:
} }
case <-ticker.C: case <-ticker.C:
s.ping() s.ping()
case _, ok := <-s.outputDone:
if !ok {
break loop
}
} }
} }
} }