Skip to content

Commit 50331cb

Browse files
committed
Fix issue #17675: make socket repr() provide local and remote addresses (if any).
1 parent 7d36e4f commit 50331cb

3 files changed

Lines changed: 40 additions & 9 deletions

File tree

Lib/socket.py

Lines changed: 26 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -103,13 +103,32 @@ def __exit__(self, *args):
103103
self.close()
104104

105105
def __repr__(self):
106-
"""Wrap __repr__() to reveal the real class name."""
107-
s = _socket.socket.__repr__(self)
108-
if s.startswith("<socket object"):
109-
s = "<%s.%s%s%s" % (self.__class__.__module__,
110-
self.__class__.__name__,
111-
getattr(self, '_closed', False) and " [closed] " or "",
112-
s[7:])
106+
"""Wrap __repr__() to reveal the real class name and socket
107+
address(es).
108+
"""
109+
closed = getattr(self, '_closed', False)
110+
s = "<%s.%s%s fd=%i, family=%i, type=%i, proto=%i" \
111+
% (self.__class__.__module__,
112+
self.__class__.__name__,
113+
" [closed]" if closed else "",
114+
self.fileno(),
115+
self.family,
116+
self.type,
117+
self.proto)
118+
if not closed:
119+
try:
120+
laddr = self.getsockname()
121+
if laddr:
122+
s += ", laddr=%s" % str(laddr)
123+
except error:
124+
pass
125+
try:
126+
raddr = self.getpeername()
127+
if raddr:
128+
s += ", raddr=%s" % str(raddr)
129+
except error:
130+
pass
131+
s += '>'
113132
return s
114133

115134
def __getstate__(self):

Lib/test/test_socket.py

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -652,8 +652,17 @@ class GeneralModuleTests(unittest.TestCase):
652652

653653
def test_repr(self):
654654
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
655-
self.addCleanup(s.close)
656-
self.assertTrue(repr(s).startswith("<socket.socket object"))
655+
with s:
656+
self.assertIn('fd=%i' % s.fileno(), repr(s))
657+
self.assertIn('family=%i' % socket.AF_INET, repr(s))
658+
self.assertIn('type=%i' % socket.SOCK_STREAM, repr(s))
659+
self.assertIn('proto=0', repr(s))
660+
self.assertIn('laddr', repr(s))
661+
self.assertNotIn('raddr', repr(s))
662+
s.bind(('127.0.0.1', 0))
663+
self.assertIn(str(s.getsockname()), repr(s))
664+
self.assertIn('[closed]', repr(s))
665+
self.assertNotIn('laddr', repr(s))
657666

658667
def test_weakref(self):
659668
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

Misc/NEWS

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,9 @@ Core and Builtins
3232
Library
3333
-------
3434

35+
- Issue #17675: socket repr() provides local and remote addresses (if any).
36+
Patch by Giampaolo Rodola'
37+
3538
- Issue #17093: Make the ABCs in importlib.abc provide default values or raise
3639
reasonable exceptions for their methods to make them more amenable to super()
3740
calls.

0 commit comments

Comments
 (0)