Skip to content
Merged
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
3 changes: 3 additions & 0 deletions Doc/library/pprint.rst
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,9 @@ width constraint.

Dictionaries are sorted by key before the display is computed.

.. versionchanged:: 3.9
Added support for pretty-printing :class:`types.SimpleNamespace`.

The :mod:`pprint` module defines one class:

.. First the implementation class:
Expand Down
6 changes: 6 additions & 0 deletions Doc/whatsnew/3.9.rst
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,12 @@ threads were never supported in subinterpreters. Previously, the subinterpreter
finalization crashed with a Pyton fatal error if a daemon thread was still
running.

pprint
------

:mod:`pprint` can now pretty-print :class:`types.SimpleNamespace`.
(Contributed by Carl Bordum Hansen in :issue:`37376`.)


Optimizations
=============
Expand Down
27 changes: 27 additions & 0 deletions Lib/pprint.py
Original file line number Diff line number Diff line change
Expand Up @@ -342,6 +342,33 @@ def _pprint_mappingproxy(self, object, stream, indent, allowance, context, level

_dispatch[_types.MappingProxyType.__repr__] = _pprint_mappingproxy

def _pprint_simplenamespace(self, object, stream, indent, allowance, context, level):
if type(object) is _types.SimpleNamespace:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for updating this. It's more clear now (as a reader).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

And better. Checking the class by comparing the class name to a string is a bit wonky :D Thanks for pointing out, what I was actually doing.

# The SimpleNamespace repr is "namespace" instead of the class
# name, so we do the same here. For subclasses; use the class name.
cls_name = 'namespace'
else:
cls_name = object.__class__.__name__
indent += len(cls_name) + 1
delimnl = ',\n' + ' ' * indent
items = object.__dict__.items()
last_index = len(items) - 1

stream.write(cls_name + '(')
for i, (key, ent) in enumerate(items):
stream.write(key)
stream.write('=')

last = i == last_index
self._format(ent, stream, indent + len(key) + 1,
allowance if last else 1,
context, level)
if not last:
stream.write(delimnl)
stream.write(')')

_dispatch[_types.SimpleNamespace.__repr__] = _pprint_simplenamespace

def _format_dict_items(self, items, stream, indent, allowance, context,
level):
write = stream.write
Expand Down
59 changes: 59 additions & 0 deletions Lib/test/test_pprint.py
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,65 @@ def test_mapping_proxy(self):
('lazy', 7),
('dog', 8)]))""")

def test_empty_simple_namespace(self):
ns = types.SimpleNamespace()
formatted = pprint.pformat(ns)
self.assertEqual(formatted, "namespace()")

def test_small_simple_namespace(self):
ns = types.SimpleNamespace(a=1, b=2)
formatted = pprint.pformat(ns)
self.assertEqual(formatted, "namespace(a=1, b=2)")

def test_simple_namespace(self):
ns = types.SimpleNamespace(
the=0,
quick=1,
brown=2,
fox=3,
jumped=4,
over=5,
a=6,
lazy=7,
dog=8,
)
formatted = pprint.pformat(ns, width=60)
self.assertEqual(formatted, """\
namespace(the=0,
quick=1,
brown=2,
fox=3,
jumped=4,
over=5,
a=6,
lazy=7,
dog=8)""")

def test_simple_namespace_subclass(self):
class AdvancedNamespace(types.SimpleNamespace): pass
ns = AdvancedNamespace(
the=0,
quick=1,
brown=2,
fox=3,
jumped=4,
over=5,
a=6,
lazy=7,
dog=8,
)
formatted = pprint.pformat(ns, width=60)
self.assertEqual(formatted, """\
AdvancedNamespace(the=0,
quick=1,
brown=2,
fox=3,
jumped=4,
over=5,
a=6,
lazy=7,
dog=8)""")

def test_subclassing(self):
o = {'names with spaces': 'should be presented using repr()',
'others.should.not.be': 'like.this'}
Expand Down
1 change: 1 addition & 0 deletions Misc/ACKS
Original file line number Diff line number Diff line change
Expand Up @@ -628,6 +628,7 @@ Mark Hammond
Harald Hanche-Olsen
Manus Hand
Milton L. Hankins
Carl Bordum Hansen
Stephen Hansen
Barry Hantman
Lynda Hardman
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
:mod:`pprint` now has support for :class:`types.SimpleNamespace`. Patch by Carl
Bordum Hansen.