Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions lib/protocol/websocket/connection.rb
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,8 @@ def close_write(error = nil)
else
send_close
end
rescue
@state = :closed
end

# Close the connection gracefully. This will send a close frame and wait for the remote end to respond with a close frame. Any data received after the close frame is sent will be ignored. If you want to process this data, use {#close_write} instead, and read the data before calling {#close}.
Expand Down
4 changes: 4 additions & 0 deletions releases.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# Releases

## Unreleased

- If `Connection#close_write` fails, the connection will now be fully closed to prevent hanging connections.

## v0.21.0

- All frame reading and writing logic has been consolidated into `Framer` to improve performance.
Expand Down
37 changes: 37 additions & 0 deletions test/protocol/websocket/connection.rb
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,43 @@

expect(connection).to be(:closed?)
end

it "does not raise if the underlying stream is closed" do
server.close

expect do
connection.close_write
end.not.to raise_exception

expect(connection).to be(:closed?)
end

it "does not raise if the underlying stream is closed (with error)" do
server.close

expect do
connection.close_write(RuntimeError.new("something went wrong"))
end.not.to raise_exception

expect(connection).to be(:closed?)
end

it "is not closed when close_write succeeds" do
connection.close_write

expect(connection).not.to be(:closed?)
end

it "can still read after a successful close_write" do
text_frame = Protocol::WebSocket::TextFrame.new(true)
text_frame.pack("Hello")
client.write_frame(text_frame)

connection.close_write

message = connection.read
expect(message).to be == "Hello"
end
end

with "#shutdown" do
Expand Down
Loading