-
-
Notifications
You must be signed in to change notification settings - Fork 111
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Backport CPython PR 26067 #132
Conversation
Not sure why that test is failing only on 3.9; it's a bit weird. I'll try to take another look tomorrow, but any suggestions are welcome :) |
I figured it out -- |
Sorry for being a pain, but could we split out the flake8 changes for a cleaner history? |
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My understanding of typing internals is limited, but this LGTM, apart from the comment about flake8 and a question below.
@@ -581,12 +609,12 @@ def _proto_hook(other): | |||
if not cls.__dict__.get('_is_protocol', None): | |||
return NotImplemented | |||
if not getattr(cls, '_is_runtime_protocol', False): | |||
if _caller(depth=3) in {'abc', 'functools'}: | |||
if _allow_reckless_class_checks(): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is it correct that the depth is changed from 3 to 4?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, because by adding a new function that the code has to pass through before it gets to the sys._getframe
call, the call stack becomes "another frame deep"
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I could just have looked at _caller
and figured that out myself. 🤦
return NotImplemented | ||
raise TypeError("Instance and class checks can only be used with" | ||
" @runtime protocols") | ||
if not _is_callable_members_only(cls): | ||
if _caller(depth=3) in {'abc', 'functools'}: | ||
if _allow_reckless_class_checks(): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here as well?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same as above
Thanks! |
This backports the CPython PR python/cpython#26067, which was backported to Python 3.10 but no earlier in the CPython repo.
(It was initially backported to 3.9, but the backport was reverted: python/cpython#26077.)
Since we're now backporting a bugfix to <=3.9, this means that we re-implement
Protocol
/runtime_checkable
on <=3.9, rather than on just 3.7. Doing this requires a change to_get_protocol_attrs
; I also tweakedtyping_extensions.runtime_checkable
so that it also works ontyping.Protocol
, iftyping.Protocol
exists.