summaryrefslogtreecommitdiffstats
path: root/Lib/email
diff options
context:
space:
mode:
authorR David Murray <rdmurray@bitdance.com>2012-05-31 22:00:45 (GMT)
committerR David Murray <rdmurray@bitdance.com>2012-05-31 22:00:45 (GMT)
commit1be413e366be7bed676074b7f395b2a20a10ac47 (patch)
tree1fb22c928ffb044049b606de24ab68035a941b1f /Lib/email
parent8e0ed333b9d52477a90ed36fdf0eb31c3d432e91 (diff)
downloadcpython-1be413e366be7bed676074b7f395b2a20a10ac47.zip
cpython-1be413e366be7bed676074b7f395b2a20a10ac47.tar.gz
cpython-1be413e366be7bed676074b7f395b2a20a10ac47.tar.bz2
Don't use metaclasses when class decorators can do the job.
Thanks to Nick Coghlan for pointing out that I'd forgotten about class decorators.
Diffstat (limited to 'Lib/email')
-rw-r--r--Lib/email/_policybase.py45
-rw-r--r--Lib/email/policy.py3
2 files changed, 22 insertions, 26 deletions
diff --git a/Lib/email/_policybase.py b/Lib/email/_policybase.py
index d5e8df9..8106114 100644
--- a/Lib/email/_policybase.py
+++ b/Lib/email/_policybase.py
@@ -91,31 +91,25 @@ class _PolicyBase:
return self.clone(**other.__dict__)
-# Conceptually this isn't a subclass of ABCMeta, but since we want Policy to
-# use ABCMeta as a metaclass *and* we want it to use this one as well, we have
-# to make this one a subclas of ABCMeta.
-class _DocstringExtenderMetaclass(abc.ABCMeta):
-
- def __new__(meta, classname, bases, classdict):
- if classdict.get('__doc__') and classdict['__doc__'].startswith('+'):
- classdict['__doc__'] = meta._append_doc(bases[0].__doc__,
- classdict['__doc__'])
- for name, attr in classdict.items():
- if attr.__doc__ and attr.__doc__.startswith('+'):
- for cls in (cls for base in bases for cls in base.mro()):
- doc = getattr(getattr(cls, name), '__doc__')
- if doc:
- attr.__doc__ = meta._append_doc(doc, attr.__doc__)
- break
- return super().__new__(meta, classname, bases, classdict)
-
- @staticmethod
- def _append_doc(doc, added_doc):
- added_doc = added_doc.split('\n', 1)[1]
- return doc + '\n' + added_doc
-
-
-class Policy(_PolicyBase, metaclass=_DocstringExtenderMetaclass):
+def _append_doc(doc, added_doc):
+ doc = doc.rsplit('\n', 1)[0]
+ added_doc = added_doc.split('\n', 1)[1]
+ return doc + '\n' + added_doc
+
+def _extend_docstrings(cls):
+ if cls.__doc__ and cls.__doc__.startswith('+'):
+ cls.__doc__ = _append_doc(cls.__bases__[0].__doc__, cls.__doc__)
+ for name, attr in cls.__dict__.items():
+ if attr.__doc__ and attr.__doc__.startswith('+'):
+ for c in (c for base in cls.__bases__ for c in base.mro()):
+ doc = getattr(getattr(c, name), '__doc__')
+ if doc:
+ attr.__doc__ = _append_doc(doc, attr.__doc__)
+ break
+ return cls
+
+
+class Policy(_PolicyBase, metaclass=abc.ABCMeta):
r"""Controls for how messages are interpreted and formatted.
@@ -264,6 +258,7 @@ class Policy(_PolicyBase, metaclass=_DocstringExtenderMetaclass):
raise NotImplementedError
+@_extend_docstrings
class Compat32(Policy):
"""+
diff --git a/Lib/email/policy.py b/Lib/email/policy.py
index bfffb45..32cad0d 100644
--- a/Lib/email/policy.py
+++ b/Lib/email/policy.py
@@ -2,7 +2,7 @@
code that adds all the email6 features.
"""
-from email._policybase import Policy, Compat32, compat32
+from email._policybase import Policy, Compat32, compat32, _extend_docstrings
from email.utils import _has_surrogates
from email.headerregistry import HeaderRegistry as HeaderRegistry
@@ -17,6 +17,7 @@ __all__ = [
'HTTP',
]
+@_extend_docstrings
class EmailPolicy(Policy):
"""+