Skip to content

Wrap remaining transport exceptions in Upcheck::ConnectionError#2

Open
Montana wants to merge 1 commit into
thoughtbot:mainfrom
Montana:http-client-transport-errors
Open

Wrap remaining transport exceptions in Upcheck::ConnectionError#2
Montana wants to merge 1 commit into
thoughtbot:mainfrom
Montana:http-client-transport-errors

Conversation

@Montana

@Montana Montana commented Jul 7, 2026

Copy link
Copy Markdown

Hey all,

Upcheck::HTTPClient rescues timeouts, SocketError, and a few Errno classes, but several other common transport failures leak to callers as raw exceptions, breaking the README's promise that "every failure raises a specific subclass of Upcheck::Error":

  • OpenSSL::SSL::SSLError — TLS handshake failures (expired/invalid certs, protocol mismatch)
  • Errno::ECONNRESET — connection reset by peer (I reproduced this by pointing the client at a server that closes the socket during the TLS handshake)
  • EOFError — server closes the connection mid-response
  • Net::HTTPBadResponse — server responds with something that isn't HTTP

Reproduction against a local socket that accepts and immediately closes connections:

client = Upcheck::HTTPClient.new
client.get_json("https://127.0.0.1:#{port}/api/v2/status.json")
# => Errno::ECONNRESET: Connection reset by peer - SSL_connect
client.get_json("http://127.0.0.1:#{port}/x")
# => EOFError: end of file reached

This matters for a status-checking gem in particular: callers rescuing Upcheck::Error around a provider.status call (as the README suggests) will still crash on exactly the kind of network weirdness that tends to accompany an upstream outage.

Fix

Add the four exception classes to the existing ConnectionError rescue in HTTPClient#get, and require "openssl" explicitly since the rescue now references its constant.

All four are connection-level failures, so ConnectionError (rather than a new subclass) seemed like the right home — happy to split them out if you'd prefer.

Testing

Four new examples in http_client_spec.rb using WebMock's to_raise, one per exception class, mirroring the existing SocketError example. Full suite: 95 examples, 0 failures. Also verified against a real local TCP socket (not just WebMock) that ECONNRESET and EOFError are now wrapped.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant