Skip to content

Commit 8707949

Browse files
MikaelSmithJens-G
authored andcommitted
THRIFT-792: Preserve last connect exception
Preserves the last exception when TSocket connect fails to provide more context to callers. The exceptions are already logged at info level, but callers may suppress that or want to view details in the exception, so attach the last as an inner layer of TTransportException, similar to gaierror above.
1 parent 8226712 commit 8707949

File tree

2 files changed

+15
-2
lines changed

2 files changed

+15
-2
lines changed

lib/py/src/transport/TSocket.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,8 @@ def open(self):
133133
msg = 'failed to resolve sockaddr for ' + str(self._address)
134134
logger.exception(msg)
135135
raise TTransportException(type=TTransportException.NOT_OPEN, message=msg, inner=gai)
136+
# Preserve the last exception to report if all addresses fail.
137+
last_exc = None
136138
for family, socktype, _, _, sockaddr in addrs:
137139
handle = self._do_open(family, socktype)
138140

@@ -145,13 +147,14 @@ def open(self):
145147
handle.connect(sockaddr)
146148
self.handle = handle
147149
return
148-
except socket.error:
150+
except socket.error as e:
149151
handle.close()
150152
logger.info('Could not connect to %s', sockaddr, exc_info=True)
153+
last_exc = e
151154
msg = 'Could not connect to any of %s' % list(map(lambda a: a[4],
152155
addrs))
153156
logger.error(msg)
154-
raise TTransportException(type=TTransportException.NOT_OPEN, message=msg)
157+
raise TTransportException(type=TTransportException.NOT_OPEN, message=msg, inner=last_exc)
155158

156159
def read(self, sz):
157160
try:

lib/py/test/test_socket.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,16 @@
3030

3131

3232
class TSocketTest(unittest.TestCase):
33+
def test_failed_connection_raises_exception(self):
34+
sock = TSocket(host="localhost", port=60606) # unused port
35+
with self.assertRaises(TTransportException) as ctx:
36+
sock.open()
37+
exc = ctx.exception
38+
self.assertEqual(exc.type, TTransportException.NOT_OPEN)
39+
self.assertIn("Could not connect to any of", exc.message)
40+
self.assertIsNotNone(exc.inner)
41+
self.assertIn("Connection refused", str(exc.inner))
42+
3343
def test_socket_readtimeout_exception(self):
3444
acc = ServerAcceptor(TServerSocket(port=0))
3545
acc.start()

0 commit comments

Comments
 (0)