summaryrefslogtreecommitdiffstats
path: root/Lib/functools.py
diff options
context:
space:
mode:
authorAlex Waygood <Alex.Waygood@Gmail.com>2021-10-28 16:02:04 (GMT)
committerGitHub <noreply@github.com>2021-10-28 16:02:04 (GMT)
commit97388c204b557f30e48a2b2ef826868702204cf2 (patch)
treec6e20a9bb0e3da86ebd1777350a1694afafa3779 /Lib/functools.py
parent8365a5b5abe51cbe4151d89a5d0a993273320067 (diff)
downloadcpython-97388c204b557f30e48a2b2ef826868702204cf2.zip
cpython-97388c204b557f30e48a2b2ef826868702204cf2.tar.gz
cpython-97388c204b557f30e48a2b2ef826868702204cf2.tar.bz2
[3.9] bpo-39679: Fix `singledispatchmethod` `classmethod`/`staticmethod` bug (GH-29087)
This commit fixes a bug in the 3.9 branch where stacking `@functools.singledispatchmethod` on top of `@classmethod` or `@staticmethod` caused an exception to be raised if the method was registered using type-annotations rather than `@method.register(int)`. Tests for this scenario were added to the 3.11 and 3.10 branches in #29034 and #29072; this commit also backports those tests to the 3.9 branch. Co-authored-by: Yurii Karabas <1998uriyyo@gmail.com> Co-authored-by: Ɓukasz Langa <lukasz@langa.pl>
Diffstat (limited to 'Lib/functools.py')
-rw-r--r--Lib/functools.py6
1 files changed, 6 insertions, 0 deletions
diff --git a/Lib/functools.py b/Lib/functools.py
index 97744a8..5054e28 100644
--- a/Lib/functools.py
+++ b/Lib/functools.py
@@ -906,6 +906,12 @@ class singledispatchmethod:
Registers a new implementation for the given *cls* on a *generic_method*.
"""
+ # bpo-39679: in Python <= 3.9, classmethods and staticmethods don't
+ # inherit __annotations__ of the wrapped function (fixed in 3.10+ as
+ # a side-effect of bpo-43682) but we need that for annotation-derived
+ # singledispatches. So we add that just-in-time here.
+ if isinstance(cls, (staticmethod, classmethod)):
+ cls.__annotations__ = getattr(cls.__func__, '__annotations__', {})
return self.dispatcher.register(cls, func=method)
def __get__(self, obj, cls=None):