Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 348f544

Browse filesBrowse files
authored
Fix most tests on Python 3.13 (#378)
1 parent 132685b commit 348f544
Copy full SHA for 348f544

File tree

4 files changed

+179
-55
lines changed
Filter options

4 files changed

+179
-55
lines changed

‎CHANGELOG.md

Copy file name to clipboardExpand all lines: CHANGELOG.md
+12-1Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,17 @@
11
# Unreleased
22

3-
- Fix tests on Python 3.13.0a6 and newer. 3.13.0a6 adds a new
3+
- Backport the `typing.NoDefault` sentinel object from Python 3.13.
4+
TypeVars, ParamSpecs and TypeVarTuples without default values now have
5+
their `__default__` attribute set to this sentinel value.
6+
- TypeVars, ParamSpecs and TypeVarTuples now have a `has_default()`
7+
method, matching `typing.TypeVar`, `typing.ParamSpec` and
8+
`typing.TypeVarTuple` on Python 3.13+.
9+
- TypeVars, ParamSpecs and TypeVarTuples with `default=None` passed to
10+
their constructors now have their `__default__` attribute set to `None`
11+
at runtime rather than `types.NoneType`.
12+
- Fix most tests for `TypeVar`, `ParamSpec` and `TypeVarTuple` on Python
13+
3.13.0b1 and newer.
14+
- Fix `Protocol` tests on Python 3.13.0a6 and newer. 3.13.0a6 adds a new
415
`__static_attributes__` attribute to all classes in Python,
516
which broke some assumptions made by the implementation of
617
`typing_extensions.Protocol`. Similarly, 3.13.0b1 adds the new

‎doc/index.rst

Copy file name to clipboardExpand all lines: doc/index.rst
+52-4Lines changed: 52 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -253,13 +253,19 @@ Special typing primitives
253253

254254
The improvements from Python 3.10 and 3.11 were backported.
255255

256+
.. data:: NoDefault
257+
258+
See :py:class:`typing.NoDefault`. In ``typing`` since 3.13.0.
259+
260+
.. versionadded:: 4.12.0
261+
256262
.. data:: NotRequired
257263

258264
See :py:data:`typing.NotRequired` and :pep:`655`. In ``typing`` since 3.11.
259265

260266
.. versionadded:: 4.0.0
261267

262-
.. class:: ParamSpec(name, *, default=...)
268+
.. class:: ParamSpec(name, *, default=NoDefault)
263269

264270
See :py:class:`typing.ParamSpec` and :pep:`612`. In ``typing`` since 3.10.
265271

@@ -284,6 +290,20 @@ Special typing primitives
284290
Passing an ellipsis literal (``...``) to *default* now works on Python
285291
3.10 and lower.
286292

293+
.. versionchanged:: 4.12.0
294+
295+
The :attr:`!__default__` attribute is now set to ``None`` if
296+
``default=None`` is passed, and to :data:`NoDefault` if no value is passed.
297+
298+
Previously, passing ``None`` would result in :attr:`!__default__` being set
299+
to :py:class:`types.NoneType`, and passing no value for the parameter would
300+
result in :attr:`!__default__` being set to ``None``.
301+
302+
.. versionchanged:: 4.12.0
303+
304+
ParamSpecs now have a ``has_default()`` method, for compatibility
305+
with :py:class:`typing.ParamSpec` on Python 3.13+.
306+
287307
.. class:: ParamSpecArgs
288308

289309
.. class:: ParamSpecKwargs
@@ -395,7 +415,7 @@ Special typing primitives
395415
are mutable if they do not carry the :data:`ReadOnly` qualifier.
396416

397417
.. versionadded:: 4.9.0
398-
418+
399419
The experimental ``closed`` keyword argument and the special key
400420
``__extra_items__`` proposed in :pep:`728` are supported.
401421

@@ -466,7 +486,7 @@ Special typing primitives
466486
when ``closed=True`` is given were supported.
467487

468488
.. class:: TypeVar(name, *constraints, bound=None, covariant=False,
469-
contravariant=False, infer_variance=False, default=...)
489+
contravariant=False, infer_variance=False, default=NoDefault)
470490

471491
See :py:class:`typing.TypeVar`.
472492

@@ -484,7 +504,21 @@ Special typing primitives
484504

485505
The implementation was changed for compatibility with Python 3.12.
486506

487-
.. class:: TypeVarTuple(name, *, default=...)
507+
.. versionchanged:: 4.12.0
508+
509+
The :attr:`!__default__` attribute is now set to ``None`` if
510+
``default=None`` is passed, and to :data:`NoDefault` if no value is passed.
511+
512+
Previously, passing ``None`` would result in :attr:`!__default__` being set
513+
to :py:class:`types.NoneType`, and passing no value for the parameter would
514+
result in :attr:`!__default__` being set to ``None``.
515+
516+
.. versionchanged:: 4.12.0
517+
518+
TypeVars now have a ``has_default()`` method, for compatibility
519+
with :py:class:`typing.TypeVar` on Python 3.13+.
520+
521+
.. class:: TypeVarTuple(name, *, default=NoDefault)
488522

489523
See :py:class:`typing.TypeVarTuple` and :pep:`646`. In ``typing`` since 3.11.
490524

@@ -501,6 +535,20 @@ Special typing primitives
501535

502536
The implementation was changed for compatibility with Python 3.12.
503537

538+
.. versionchanged:: 4.12.0
539+
540+
The :attr:`!__default__` attribute is now set to ``None`` if
541+
``default=None`` is passed, and to :data:`NoDefault` if no value is passed.
542+
543+
Previously, passing ``None`` would result in :attr:`!__default__` being set
544+
to :py:class:`types.NoneType`, and passing no value for the parameter would
545+
result in :attr:`!__default__` being set to ``None``.
546+
547+
.. versionchanged:: 4.12.0
548+
549+
TypeVarTuples now have a ``has_default()`` method, for compatibility
550+
with :py:class:`typing.TypeVarTuple` on Python 3.13+.
551+
504552
.. data:: Unpack
505553

506554
See :py:data:`typing.Unpack` and :pep:`646`. In ``typing`` since 3.11.

‎src/test_typing_extensions.py

Copy file name to clipboardExpand all lines: src/test_typing_extensions.py
+37-10Lines changed: 37 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
from typing_extensions import clear_overloads, get_overloads, overload
3939
from typing_extensions import NamedTuple, TypeIs
4040
from typing_extensions import override, deprecated, Buffer, TypeAliasType, TypeVar, get_protocol_members, is_protocol
41-
from typing_extensions import Doc
41+
from typing_extensions import Doc, NoDefault
4242
from _typed_dict_test_helper import Foo, FooGeneric, VeryAnnotated
4343

4444
# Flags used to mark tests that only apply after a specific
@@ -59,9 +59,9 @@
5959
# versions, but not all
6060
HAS_FORWARD_MODULE = "module" in inspect.signature(typing._type_check).parameters
6161

62-
skip_if_early_py313_alpha = skipIf(
63-
sys.version_info[:4] == (3, 13, 0, 'alpha') and sys.version_info.serial < 3,
64-
"Bugfixes will be released in 3.13.0a3"
62+
skip_if_py313_beta_1 = skipIf(
63+
sys.version_info[:5] == (3, 13, 0, 'beta', 1),
64+
"Bugfixes will be released in 3.13.0b2"
6565
)
6666

6767
ANN_MODULE_SOURCE = '''\
@@ -3485,7 +3485,6 @@ def method(self) -> None: ...
34853485
self.assertIsInstance(Foo(), ProtocolWithMixedMembers)
34863486
self.assertNotIsInstance(42, ProtocolWithMixedMembers)
34873487

3488-
@skip_if_early_py313_alpha
34893488
def test_protocol_issubclass_error_message(self):
34903489
@runtime_checkable
34913490
class Vec2D(Protocol):
@@ -5917,7 +5916,6 @@ class GenericNamedTuple(NamedTuple, Generic[T]):
59175916

59185917
self.assertEqual(CallNamedTuple.__orig_bases__, (NamedTuple,))
59195918

5920-
@skip_if_early_py313_alpha
59215919
def test_setname_called_on_values_in_class_dictionary(self):
59225920
class Vanilla:
59235921
def __set_name__(self, owner, name):
@@ -5989,7 +5987,6 @@ class NamedTupleClass(NamedTuple):
59895987
TYPING_3_12_0,
59905988
"__set_name__ behaviour changed on py312+ to use BaseException.add_note()"
59915989
)
5992-
@skip_if_early_py313_alpha
59935990
def test_setname_raises_the_same_as_on_other_classes_py312_plus(self):
59945991
class CustomException(BaseException): pass
59955992

@@ -6029,7 +6026,6 @@ class NamedTupleClass(NamedTuple):
60296026
normal_exception.__notes__[0].replace("NormalClass", "NamedTupleClass")
60306027
)
60316028

6032-
@skip_if_early_py313_alpha
60336029
def test_strange_errors_when_accessing_set_name_itself(self):
60346030
class CustomException(Exception): pass
60356031

@@ -6207,12 +6203,15 @@ class A(Generic[T]): ...
62076203
def test_typevar_none(self):
62086204
U = typing_extensions.TypeVar('U')
62096205
U_None = typing_extensions.TypeVar('U_None', default=None)
6210-
self.assertEqual(U.__default__, None)
6211-
self.assertEqual(U_None.__default__, type(None))
6206+
self.assertIs(U.__default__, NoDefault)
6207+
self.assertFalse(U.has_default())
6208+
self.assertEqual(U_None.__default__, None)
6209+
self.assertTrue(U_None.has_default())
62126210

62136211
def test_paramspec(self):
62146212
P = ParamSpec('P', default=(str, int))
62156213
self.assertEqual(P.__default__, (str, int))
6214+
self.assertTrue(P.has_default())
62166215
self.assertIsInstance(P, ParamSpec)
62176216
if hasattr(typing, "ParamSpec"):
62186217
self.assertIsInstance(P, typing.ParamSpec)
@@ -6225,11 +6224,13 @@ class A(Generic[P]): ...
62256224

62266225
P_default = ParamSpec('P_default', default=...)
62276226
self.assertIs(P_default.__default__, ...)
6227+
self.assertTrue(P_default.has_default())
62286228

62296229
def test_typevartuple(self):
62306230
Ts = TypeVarTuple('Ts', default=Unpack[Tuple[str, int]])
62316231
self.assertEqual(Ts.__default__, Unpack[Tuple[str, int]])
62326232
self.assertIsInstance(Ts, TypeVarTuple)
6233+
self.assertTrue(Ts.has_default())
62336234
if hasattr(typing, "TypeVarTuple"):
62346235
self.assertIsInstance(Ts, typing.TypeVarTuple)
62356236
typing_Ts = typing.TypeVarTuple('Ts')
@@ -6276,6 +6277,32 @@ def test_pickle(self):
62766277
self.assertEqual(z.__default__, typevar.__default__)
62776278

62786279

6280+
class NoDefaultTests(BaseTestCase):
6281+
@skip_if_py313_beta_1
6282+
def test_pickling(self):
6283+
for proto in range(pickle.HIGHEST_PROTOCOL + 1):
6284+
s = pickle.dumps(NoDefault, proto)
6285+
loaded = pickle.loads(s)
6286+
self.assertIs(NoDefault, loaded)
6287+
6288+
def test_constructor(self):
6289+
self.assertIs(NoDefault, type(NoDefault)())
6290+
with self.assertRaises(TypeError):
6291+
type(NoDefault)(1)
6292+
6293+
def test_repr(self):
6294+
self.assertRegex(repr(NoDefault), r'typing(_extensions)?\.NoDefault')
6295+
6296+
def test_no_call(self):
6297+
with self.assertRaises(TypeError):
6298+
NoDefault()
6299+
6300+
@skip_if_py313_beta_1
6301+
def test_immutable(self):
6302+
with self.assertRaises(AttributeError):
6303+
NoDefault.foo = 'bar'
6304+
6305+
62796306
class TypeVarInferVarianceTests(BaseTestCase):
62806307
def test_typevar(self):
62816308
T = typing_extensions.TypeVar('T')

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.