Rename typing._collect_parameters by JelleZijlstra · Pull Request #118900 · python/cpython · GitHub
Skip to content

Rename typing._collect_parameters - #118900

Merged
JelleZijlstra merged 6 commits into
python:mainfrom
JelleZijlstra:collectparams
May 10, 2024
Merged

Rename typing._collect_parameters#118900
JelleZijlstra merged 6 commits into
python:mainfrom
JelleZijlstra:collectparams

Conversation

@JelleZijlstra

Copy link
Copy Markdown
Member

function. Unfortunately, released versions of typing_extensions
monkeypatch this function without the extra parameter, which makes
it so things break badly if current main is used with typing_extensions.

% ~/py/cpython/python.exe test_typing_extensions.py
Traceback (most recent call last):
  File "/Users/jelle/py/typing_extensions/src/test_typing_extensions.py", line 42, in <module>
    from _typed_dict_test_helper import Foo, FooGeneric, VeryAnnotated
  File "/Users/jelle/py/typing_extensions/src/_typed_dict_test_helper.py", line 17, in <module>
    class FooGeneric(TypedDict, Generic[T]):
                                ~~~~~~~^^^
  File "/Users/jelle/py/cpython/Lib/typing.py", line 431, in inner
    return func(*args, **kwds)
  File "/Users/jelle/py/cpython/Lib/typing.py", line 1243, in _generic_class_getitem
    return _GenericAlias(cls, args)
  File "/Users/jelle/py/cpython/Lib/typing.py", line 1420, in __init__
    self.__parameters__ = _collect_parameters(
                          ~~~~~~~~~~~~~~~~~~~^
        args,
        ^^^^^
        enforce_default_ordering=enforce_default_ordering,
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
TypeError: _collect_parameters() got an unexpected keyword argument 'enforce_default_ordering'

Fortunately, the monkeypatching is not needed on Python 3.13, because CPython
now implements PEP 696. By renaming the function, we prevent the monkeypatch
from breaking typing.py internals.

function. Unfortunately, released versions of typing_extensions
monkeypatch this function without the extra parameter, which makes
it so things break badly if current main is used with typing_extensions.

```
% ~/py/cpython/python.exe test_typing_extensions.py
Traceback (most recent call last):
  File "/Users/jelle/py/typing_extensions/src/test_typing_extensions.py", line 42, in <module>
    from _typed_dict_test_helper import Foo, FooGeneric, VeryAnnotated
  File "/Users/jelle/py/typing_extensions/src/_typed_dict_test_helper.py", line 17, in <module>
    class FooGeneric(TypedDict, Generic[T]):
                                ~~~~~~~^^^
  File "/Users/jelle/py/cpython/Lib/typing.py", line 431, in inner
    return func(*args, **kwds)
  File "/Users/jelle/py/cpython/Lib/typing.py", line 1243, in _generic_class_getitem
    return _GenericAlias(cls, args)
  File "/Users/jelle/py/cpython/Lib/typing.py", line 1420, in __init__
    self.__parameters__ = _collect_parameters(
                          ~~~~~~~~~~~~~~~~~~~^
        args,
        ^^^^^
        enforce_default_ordering=enforce_default_ordering,
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
TypeError: _collect_parameters() got an unexpected keyword argument 'enforce_default_ordering'
```

Fortunately, the monkeypatching is not needed on Python 3.13, because CPython
now implements PEP 696. By renaming the function, we prevent the monkeypatch
from breaking typing.py internals.
@AlexWaygood

AlexWaygood commented May 10, 2024

Copy link
Copy Markdown
Member

@JelleZijlstra

Copy link
Copy Markdown
Member Author

But I think already-released versions of typing_extensions are badly broken anyway on Python 3.13, due to the error pointed out in python/typing_extensions#377 (comment)

I think that error shows up only if you use typing_extensions.TypeVar though, while the error this PR fixes breaks any use of Generic after typing_extensions is imported, which feels much worse.

There are some uses of this function in the wild, which this change would break... https://github.com/wyfo/apischema/blob/d48cc010c417e9c49db25b7a8683621b3c305b44/apischema/typing.py#L59-L62

I think we could address this by keeping an alias _collect_parameters = _collect_type_parameters (or a wrapper function that raises DeprecationWarning).

@AlexWaygood

Copy link
Copy Markdown
Member

Okay, sounds reasonable.

I think we could address this by keeping an alias _collect_parameters = _collect_type_parameters (or a wrapper function that raises DeprecationWarning).

Or we could do this in the __getattr__ method down at the bottom? (With do_the_deprecation_warning() replaced by the appropriate logic to do a deprecation warning)

--- a/Lib/typing.py
+++ b/Lib/typing.py
@@ -3770,6 +3770,9 @@ def __getattr__(attr):
     elif attr in {"ContextManager", "AsyncContextManager"}:
         import contextlib
         obj = _alias(getattr(contextlib, f"Abstract{attr}"), 2, name=attr, defaults=(bool | None,))
+    elif attr == "_collect_parameters":
+        do_the_deprecation_warning()
+        return _collect_type_parameters
     else:
         raise AttributeError(f"module {__name__!r} has no attribute {attr!r}")
     globals()[attr] = obj

Comment thread Lib/typing.py Outdated

@AlexWaygood AlexWaygood left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Thanks!

Comment thread Lib/test/test_typing.py Outdated
Co-authored-by: Alex Waygood <Alex.Waygood@Gmail.com>
@JelleZijlstra
JelleZijlstra enabled auto-merge (squash) May 10, 2024 16:21
@JelleZijlstra
JelleZijlstra merged commit ec9d12b into python:main May 10, 2024
@miss-islington-app

Copy link
Copy Markdown

Thanks @JelleZijlstra for the PR 🌮🎉.. I'm working now to backport this PR to: 3.13.
🐍🍒⛏🤖

miss-islington pushed a commit to miss-islington/cpython that referenced this pull request May 10, 2024
Unfortunately, released versions of typing_extensions
monkeypatch this function without the extra parameter, which makes
it so things break badly if current main is used with typing_extensions.

Fortunately, the monkeypatching is not needed on Python 3.13, because CPython
now implements PEP 696. By renaming the function, we prevent the monkeypatch
from breaking typing.py internals.

We keep the old name (raising a DeprecationWarning) to help other external users who call it.
(cherry picked from commit ec9d12b)

Co-authored-by: Jelle Zijlstra <jelle.zijlstra@gmail.com>
@bedevere-app

bedevere-app Bot commented May 10, 2024

Copy link
Copy Markdown

GH-118917 is a backport of this pull request to the 3.13 branch.

@bedevere-app bedevere-app Bot removed the needs backport to 3.13 bugs and security fixes label May 10, 2024
@JelleZijlstra
JelleZijlstra deleted the collectparams branch May 10, 2024 17:08
AlexWaygood pushed a commit that referenced this pull request May 10, 2024
Co-authored-by: Jelle Zijlstra <jelle.zijlstra@gmail.com>
@bedevere-bot

Copy link
Copy Markdown

estyxx pushed a commit to estyxx/cpython that referenced this pull request Jul 17, 2024
Unfortunately, released versions of typing_extensions
monkeypatch this function without the extra parameter, which makes
it so things break badly if current main is used with typing_extensions.

Fortunately, the monkeypatching is not needed on Python 3.13, because CPython
now implements PEP 696. By renaming the function, we prevent the monkeypatch
from breaking typing.py internals.

We keep the old name (raising a DeprecationWarning) to help other external users who call it.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants