Skip to content

Commit

Permalink
Improve websocket write handling
Browse files Browse the repository at this point in the history
Increase the buffer size of the write channel to 1024. This way adding messages will never block if e.g. at the same time the connection is closed. If the buffer is full, return an error, as sending isn’t possible.

This fixes #42
  • Loading branch information
DerAndereAndi committed Nov 26, 2024
1 parent d68708c commit 3b345c3
Show file tree
Hide file tree
Showing 2 changed files with 26 additions and 3 deletions.
12 changes: 9 additions & 3 deletions ws/websocket.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,8 +80,8 @@ func (w *WebsocketConnection) isConnClosed() bool {
}

func (w *WebsocketConnection) run() {
w.shipWriteChannel = make(chan []byte, 1) // Send outgoing ship messages
w.closeChannel = make(chan struct{}, 1) // Listen to close events
w.shipWriteChannel = make(chan []byte, 1024) // Send outgoing ship messages
w.closeChannel = make(chan struct{}, 1) // Listen to close events

go w.readShipPump()
go w.writeShipPump()
Expand Down Expand Up @@ -258,7 +258,13 @@ func (w *WebsocketConnection) WriteMessageToWebsocketConnection(message []byte)
return errors.New(connIsClosedError)
}

w.shipWriteChannel <- message
select {
case w.shipWriteChannel <- message:
default:
// too many messages are pending, this doesn't look good
return errors.New("could not send message, buffer is full")
}

return nil
}

Expand Down
17 changes: 17 additions & 0 deletions ws/websocket_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,23 @@ func (s *WebsocketSuite) TestConnectionClose() {
assert.NotNil(s.T(), err)
}

func (s *WebsocketSuite) TestWriteBufferFull() {
amountNil := 0
amountNotNil := 0
for i := 0; i < 10000; i++ {
msg := []byte{1}
msg = append(msg, []byte("message")...)
err := s.sut.WriteMessageToWebsocketConnection(msg)
if err == nil {
amountNil++
} else {
amountNotNil++
}
}
assert.Greater(s.T(), amountNotNil, 0)
assert.Greater(s.T(), amountNil, 0)
}

func (s *WebsocketSuite) TestPingPeriod() {
isClosed, err := s.sut.IsDataConnectionClosed()
assert.Equal(s.T(), false, isClosed)
Expand Down

0 comments on commit 3b345c3

Please sign in to comment.