summaryrefslogtreecommitdiffstats
path: root/Lib
diff options
context:
space:
mode:
authorNikita Sobolev <mail@sobolevn.me>2023-03-16 14:47:30 (GMT)
committerGitHub <noreply@github.com>2023-03-16 14:47:30 (GMT)
commitfbe82fdd777cead5d6e08ac0d1da19738c19bd81 (patch)
treeb85c7bed7db51840d0b16060c9bbeaec231fe3c7 /Lib
parentb0ec6253c9cf1b22b87cd99f317dbaeb31263b20 (diff)
downloadcpython-fbe82fdd777cead5d6e08ac0d1da19738c19bd81.zip
cpython-fbe82fdd777cead5d6e08ac0d1da19738c19bd81.tar.gz
cpython-fbe82fdd777cead5d6e08ac0d1da19738c19bd81.tar.bz2
gh-102721: Improve coverage of `_collections_abc._CallableGenericAlias` (#102722)
Co-authored-by: Alex Waygood <Alex.Waygood@Gmail.com>
Diffstat (limited to 'Lib')
-rw-r--r--Lib/_collections_abc.py7
-rw-r--r--Lib/test/test_typing.py39
2 files changed, 32 insertions, 14 deletions
diff --git a/Lib/_collections_abc.py b/Lib/_collections_abc.py
index f86b91a..9d7724c 100644
--- a/Lib/_collections_abc.py
+++ b/Lib/_collections_abc.py
@@ -481,15 +481,8 @@ class _CallableGenericAlias(GenericAlias):
# rather than the default types.GenericAlias object. Most of the
# code is copied from typing's _GenericAlias and the builtin
# types.GenericAlias.
-
if not isinstance(item, tuple):
item = (item,)
- # A special case in PEP 612 where if X = Callable[P, int],
- # then X[int, str] == X[[int, str]].
- if (len(self.__parameters__) == 1
- and _is_param_expr(self.__parameters__[0])
- and item and not _is_param_expr(item[0])):
- item = (item,)
new_args = super().__getitem__(item).__args__
diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py
index 89c725c..c9f55de 100644
--- a/Lib/test/test_typing.py
+++ b/Lib/test/test_typing.py
@@ -1921,14 +1921,29 @@ class BaseCallableTests:
self.assertEqual(weakref.ref(alias)(), alias)
def test_pickle(self):
+ global T_pickle, P_pickle, TS_pickle # needed for pickling
Callable = self.Callable
- alias = Callable[[int, str], float]
- for proto in range(pickle.HIGHEST_PROTOCOL + 1):
- s = pickle.dumps(alias, proto)
- loaded = pickle.loads(s)
- self.assertEqual(alias.__origin__, loaded.__origin__)
- self.assertEqual(alias.__args__, loaded.__args__)
- self.assertEqual(alias.__parameters__, loaded.__parameters__)
+ T_pickle = TypeVar('T_pickle')
+ P_pickle = ParamSpec('P_pickle')
+ TS_pickle = TypeVarTuple('TS_pickle')
+
+ samples = [
+ Callable[[int, str], float],
+ Callable[P_pickle, int],
+ Callable[P_pickle, T_pickle],
+ Callable[Concatenate[int, P_pickle], int],
+ Callable[Concatenate[*TS_pickle, P_pickle], int],
+ ]
+ for alias in samples:
+ for proto in range(pickle.HIGHEST_PROTOCOL + 1):
+ with self.subTest(alias=alias, proto=proto):
+ s = pickle.dumps(alias, proto)
+ loaded = pickle.loads(s)
+ self.assertEqual(alias.__origin__, loaded.__origin__)
+ self.assertEqual(alias.__args__, loaded.__args__)
+ self.assertEqual(alias.__parameters__, loaded.__parameters__)
+
+ del T_pickle, P_pickle, TS_pickle # cleaning up global state
def test_var_substitution(self):
Callable = self.Callable
@@ -1954,6 +1969,16 @@ class BaseCallableTests:
self.assertEqual(C5[int, str, float],
Callable[[typing.List[int], tuple[str, int], float], int])
+ def test_type_subst_error(self):
+ Callable = self.Callable
+ P = ParamSpec('P')
+ T = TypeVar('T')
+
+ pat = "Expected a list of types, an ellipsis, ParamSpec, or Concatenate."
+
+ with self.assertRaisesRegex(TypeError, pat):
+ Callable[P, T][0, int]
+
def test_type_erasure(self):
Callable = self.Callable
class C1(Callable):