1import contextlib 2import collections 3import pickle 4import re 5import sys 6from unittest import TestCase, main, skipUnless, SkipTest, skip 7from copy import copy, deepcopy 8 9from typing import Any, NoReturn 10from typing import TypeVar, AnyStr 11from typing import T, KT, VT # Not in __all__. 12from typing import Union, Optional 13from typing import Tuple, List, MutableMapping 14from typing import Callable 15from typing import Generic, ClassVar 16from typing import cast 17from typing import get_type_hints 18from typing import no_type_check, no_type_check_decorator 19from typing import Type 20from typing import NewType 21from typing import NamedTuple 22from typing import IO, TextIO, BinaryIO 23from typing import Pattern, Match 24import abc 25import typing 26import weakref 27 28from test import mod_generics_cache 29 30 31class BaseTestCase(TestCase): 32 33 def assertIsSubclass(self, cls, class_or_tuple, msg=None): 34 if not issubclass(cls, class_or_tuple): 35 message = '%r is not a subclass of %r' % (cls, class_or_tuple) 36 if msg is not None: 37 message += ' : %s' % msg 38 raise self.failureException(message) 39 40 def assertNotIsSubclass(self, cls, class_or_tuple, msg=None): 41 if issubclass(cls, class_or_tuple): 42 message = '%r is a subclass of %r' % (cls, class_or_tuple) 43 if msg is not None: 44 message += ' : %s' % msg 45 raise self.failureException(message) 46 47 def clear_caches(self): 48 for f in typing._cleanups: 49 f() 50 51 52class Employee: 53 pass 54 55 56class Manager(Employee): 57 pass 58 59 60class Founder(Employee): 61 pass 62 63 64class ManagingFounder(Manager, Founder): 65 pass 66 67 68class AnyTests(BaseTestCase): 69 70 def test_any_instance_type_error(self): 71 with self.assertRaises(TypeError): 72 isinstance(42, Any) 73 74 def test_any_subclass_type_error(self): 75 with self.assertRaises(TypeError): 76 issubclass(Employee, Any) 77 with self.assertRaises(TypeError): 78 issubclass(Any, Employee) 79 80 def test_repr(self): 81 self.assertEqual(repr(Any), 'typing.Any') 82 83 def test_errors(self): 84 with self.assertRaises(TypeError): 85 issubclass(42, Any) 86 with self.assertRaises(TypeError): 87 Any[int] # Any is not a generic type. 88 89 def test_cannot_subclass(self): 90 with self.assertRaises(TypeError): 91 class A(Any): 92 pass 93 with self.assertRaises(TypeError): 94 class A(type(Any)): 95 pass 96 97 def test_cannot_instantiate(self): 98 with self.assertRaises(TypeError): 99 Any() 100 with self.assertRaises(TypeError): 101 type(Any)() 102 103 def test_any_works_with_alias(self): 104 # These expressions must simply not fail. 105 typing.Match[Any] 106 typing.Pattern[Any] 107 typing.IO[Any] 108 109 110class NoReturnTests(BaseTestCase): 111 112 def test_noreturn_instance_type_error(self): 113 with self.assertRaises(TypeError): 114 isinstance(42, NoReturn) 115 116 def test_noreturn_subclass_type_error(self): 117 with self.assertRaises(TypeError): 118 issubclass(Employee, NoReturn) 119 with self.assertRaises(TypeError): 120 issubclass(NoReturn, Employee) 121 122 def test_repr(self): 123 self.assertEqual(repr(NoReturn), 'typing.NoReturn') 124 125 def test_not_generic(self): 126 with self.assertRaises(TypeError): 127 NoReturn[int] 128 129 def test_cannot_subclass(self): 130 with self.assertRaises(TypeError): 131 class A(NoReturn): 132 pass 133 with self.assertRaises(TypeError): 134 class A(type(NoReturn)): 135 pass 136 137 def test_cannot_instantiate(self): 138 with self.assertRaises(TypeError): 139 NoReturn() 140 with self.assertRaises(TypeError): 141 type(NoReturn)() 142 143 144class TypeVarTests(BaseTestCase): 145 146 def test_basic_plain(self): 147 T = TypeVar('T') 148 # T equals itself. 149 self.assertEqual(T, T) 150 # T is an instance of TypeVar 151 self.assertIsInstance(T, TypeVar) 152 153 def test_typevar_instance_type_error(self): 154 T = TypeVar('T') 155 with self.assertRaises(TypeError): 156 isinstance(42, T) 157 158 def test_typevar_subclass_type_error(self): 159 T = TypeVar('T') 160 with self.assertRaises(TypeError): 161 issubclass(int, T) 162 with self.assertRaises(TypeError): 163 issubclass(T, int) 164 165 def test_constrained_error(self): 166 with self.assertRaises(TypeError): 167 X = TypeVar('X', int) 168 X 169 170 def test_union_unique(self): 171 X = TypeVar('X') 172 Y = TypeVar('Y') 173 self.assertNotEqual(X, Y) 174 self.assertEqual(Union[X], X) 175 self.assertNotEqual(Union[X], Union[X, Y]) 176 self.assertEqual(Union[X, X], X) 177 self.assertNotEqual(Union[X, int], Union[X]) 178 self.assertNotEqual(Union[X, int], Union[int]) 179 self.assertEqual(Union[X, int].__args__, (X, int)) 180 self.assertEqual(Union[X, int].__parameters__, (X,)) 181 self.assertIs(Union[X, int].__origin__, Union) 182 183 def test_union_constrained(self): 184 A = TypeVar('A', str, bytes) 185 self.assertNotEqual(Union[A, str], Union[A]) 186 187 def test_repr(self): 188 self.assertEqual(repr(T), '~T') 189 self.assertEqual(repr(KT), '~KT') 190 self.assertEqual(repr(VT), '~VT') 191 self.assertEqual(repr(AnyStr), '~AnyStr') 192 T_co = TypeVar('T_co', covariant=True) 193 self.assertEqual(repr(T_co), '+T_co') 194 T_contra = TypeVar('T_contra', contravariant=True) 195 self.assertEqual(repr(T_contra), '-T_contra') 196 197 def test_no_redefinition(self): 198 self.assertNotEqual(TypeVar('T'), TypeVar('T')) 199 self.assertNotEqual(TypeVar('T', int, str), TypeVar('T', int, str)) 200 201 def test_cannot_subclass_vars(self): 202 with self.assertRaises(TypeError): 203 class V(TypeVar('T')): 204 pass 205 206 def test_cannot_subclass_var_itself(self): 207 with self.assertRaises(TypeError): 208 class V(TypeVar): 209 pass 210 211 def test_cannot_instantiate_vars(self): 212 with self.assertRaises(TypeError): 213 TypeVar('A')() 214 215 def test_bound_errors(self): 216 with self.assertRaises(TypeError): 217 TypeVar('X', bound=42) 218 with self.assertRaises(TypeError): 219 TypeVar('X', str, float, bound=Employee) 220 221 def test_missing__name__(self): 222 # See bpo-39942 223 code = ("import typing\n" 224 "T = typing.TypeVar('T')\n" 225 ) 226 exec(code, {}) 227 228 def test_no_bivariant(self): 229 with self.assertRaises(ValueError): 230 TypeVar('T', covariant=True, contravariant=True) 231 232 233class UnionTests(BaseTestCase): 234 235 def test_basics(self): 236 u = Union[int, float] 237 self.assertNotEqual(u, Union) 238 239 def test_subclass_error(self): 240 with self.assertRaises(TypeError): 241 issubclass(int, Union) 242 with self.assertRaises(TypeError): 243 issubclass(Union, int) 244 with self.assertRaises(TypeError): 245 issubclass(int, Union[int, str]) 246 with self.assertRaises(TypeError): 247 issubclass(Union[int, str], int) 248 249 def test_union_any(self): 250 u = Union[Any] 251 self.assertEqual(u, Any) 252 u1 = Union[int, Any] 253 u2 = Union[Any, int] 254 u3 = Union[Any, object] 255 self.assertEqual(u1, u2) 256 self.assertNotEqual(u1, Any) 257 self.assertNotEqual(u2, Any) 258 self.assertNotEqual(u3, Any) 259 260 def test_union_object(self): 261 u = Union[object] 262 self.assertEqual(u, object) 263 u1 = Union[int, object] 264 u2 = Union[object, int] 265 self.assertEqual(u1, u2) 266 self.assertNotEqual(u1, object) 267 self.assertNotEqual(u2, object) 268 269 def test_unordered(self): 270 u1 = Union[int, float] 271 u2 = Union[float, int] 272 self.assertEqual(u1, u2) 273 274 def test_single_class_disappears(self): 275 t = Union[Employee] 276 self.assertIs(t, Employee) 277 278 def test_base_class_kept(self): 279 u = Union[Employee, Manager] 280 self.assertNotEqual(u, Employee) 281 self.assertIn(Employee, u.__args__) 282 self.assertIn(Manager, u.__args__) 283 284 def test_union_union(self): 285 u = Union[int, float] 286 v = Union[u, Employee] 287 self.assertEqual(v, Union[int, float, Employee]) 288 289 def test_repr(self): 290 self.assertEqual(repr(Union), 'typing.Union') 291 u = Union[Employee, int] 292 self.assertEqual(repr(u), 'typing.Union[%s.Employee, int]' % __name__) 293 u = Union[int, Employee] 294 self.assertEqual(repr(u), 'typing.Union[int, %s.Employee]' % __name__) 295 T = TypeVar('T') 296 u = Union[T, int][int] 297 self.assertEqual(repr(u), repr(int)) 298 u = Union[List[int], int] 299 self.assertEqual(repr(u), 'typing.Union[typing.List[int], int]') 300 301 def test_cannot_subclass(self): 302 with self.assertRaises(TypeError): 303 class C(Union): 304 pass 305 with self.assertRaises(TypeError): 306 class C(type(Union)): 307 pass 308 with self.assertRaises(TypeError): 309 class C(Union[int, str]): 310 pass 311 312 def test_cannot_instantiate(self): 313 with self.assertRaises(TypeError): 314 Union() 315 with self.assertRaises(TypeError): 316 type(Union)() 317 u = Union[int, float] 318 with self.assertRaises(TypeError): 319 u() 320 with self.assertRaises(TypeError): 321 type(u)() 322 323 def test_union_generalization(self): 324 self.assertFalse(Union[str, typing.Iterable[int]] == str) 325 self.assertFalse(Union[str, typing.Iterable[int]] == typing.Iterable[int]) 326 self.assertIn(str, Union[str, typing.Iterable[int]].__args__) 327 self.assertIn(typing.Iterable[int], Union[str, typing.Iterable[int]].__args__) 328 329 def test_union_compare_other(self): 330 self.assertNotEqual(Union, object) 331 self.assertNotEqual(Union, Any) 332 self.assertNotEqual(ClassVar, Union) 333 self.assertNotEqual(Optional, Union) 334 self.assertNotEqual([None], Optional) 335 self.assertNotEqual(Optional, typing.Mapping) 336 self.assertNotEqual(Optional[typing.MutableMapping], Union) 337 338 def test_optional(self): 339 o = Optional[int] 340 u = Union[int, None] 341 self.assertEqual(o, u) 342 343 def test_empty(self): 344 with self.assertRaises(TypeError): 345 Union[()] 346 347 def test_union_instance_type_error(self): 348 with self.assertRaises(TypeError): 349 isinstance(42, Union[int, str]) 350 351 def test_no_eval_union(self): 352 u = Union[int, str] 353 def f(x: u): ... 354 self.assertIs(get_type_hints(f)['x'], u) 355 356 def test_function_repr_union(self): 357 def fun() -> int: ... 358 self.assertEqual(repr(Union[fun, int]), 'typing.Union[fun, int]') 359 360 def test_union_str_pattern(self): 361 # Shouldn't crash; see http://bugs.python.org/issue25390 362 A = Union[str, Pattern] 363 A 364 365 def test_etree(self): 366 # See https://github.com/python/typing/issues/229 367 # (Only relevant for Python 2.) 368 try: 369 from xml.etree.cElementTree import Element 370 except ImportError: 371 raise SkipTest("cElementTree not found") 372 Union[Element, str] # Shouldn't crash 373 374 def Elem(*args): 375 return Element(*args) 376 377 Union[Elem, str] # Nor should this 378 379 380class TupleTests(BaseTestCase): 381 382 def test_basics(self): 383 with self.assertRaises(TypeError): 384 issubclass(Tuple, Tuple[int, str]) 385 with self.assertRaises(TypeError): 386 issubclass(tuple, Tuple[int, str]) 387 388 class TP(tuple): ... 389 self.assertTrue(issubclass(tuple, Tuple)) 390 self.assertTrue(issubclass(TP, Tuple)) 391 392 def test_equality(self): 393 self.assertEqual(Tuple[int], Tuple[int]) 394 self.assertEqual(Tuple[int, ...], Tuple[int, ...]) 395 self.assertNotEqual(Tuple[int], Tuple[int, int]) 396 self.assertNotEqual(Tuple[int], Tuple[int, ...]) 397 398 def test_tuple_subclass(self): 399 class MyTuple(tuple): 400 pass 401 self.assertTrue(issubclass(MyTuple, Tuple)) 402 403 def test_tuple_instance_type_error(self): 404 with self.assertRaises(TypeError): 405 isinstance((0, 0), Tuple[int, int]) 406 self.assertIsInstance((0, 0), Tuple) 407 408 def test_repr(self): 409 self.assertEqual(repr(Tuple), 'typing.Tuple') 410 self.assertEqual(repr(Tuple[()]), 'typing.Tuple[()]') 411 self.assertEqual(repr(Tuple[int, float]), 'typing.Tuple[int, float]') 412 self.assertEqual(repr(Tuple[int, ...]), 'typing.Tuple[int, ...]') 413 414 def test_errors(self): 415 with self.assertRaises(TypeError): 416 issubclass(42, Tuple) 417 with self.assertRaises(TypeError): 418 issubclass(42, Tuple[int]) 419 420 421class CallableTests(BaseTestCase): 422 423 def test_self_subclass(self): 424 with self.assertRaises(TypeError): 425 self.assertTrue(issubclass(type(lambda x: x), Callable[[int], int])) 426 self.assertTrue(issubclass(type(lambda x: x), Callable)) 427 428 def test_eq_hash(self): 429 self.assertEqual(Callable[[int], int], Callable[[int], int]) 430 self.assertEqual(len({Callable[[int], int], Callable[[int], int]}), 1) 431 self.assertNotEqual(Callable[[int], int], Callable[[int], str]) 432 self.assertNotEqual(Callable[[int], int], Callable[[str], int]) 433 self.assertNotEqual(Callable[[int], int], Callable[[int, int], int]) 434 self.assertNotEqual(Callable[[int], int], Callable[[], int]) 435 self.assertNotEqual(Callable[[int], int], Callable) 436 437 def test_cannot_instantiate(self): 438 with self.assertRaises(TypeError): 439 Callable() 440 with self.assertRaises(TypeError): 441 type(Callable)() 442 c = Callable[[int], str] 443 with self.assertRaises(TypeError): 444 c() 445 with self.assertRaises(TypeError): 446 type(c)() 447 448 def test_callable_wrong_forms(self): 449 with self.assertRaises(TypeError): 450 Callable[[...], int] 451 with self.assertRaises(TypeError): 452 Callable[(), int] 453 with self.assertRaises(TypeError): 454 Callable[[()], int] 455 with self.assertRaises(TypeError): 456 Callable[[int, 1], 2] 457 with self.assertRaises(TypeError): 458 Callable[int] 459 460 def test_callable_instance_works(self): 461 def f(): 462 pass 463 self.assertIsInstance(f, Callable) 464 self.assertNotIsInstance(None, Callable) 465 466 def test_callable_instance_type_error(self): 467 def f(): 468 pass 469 with self.assertRaises(TypeError): 470 self.assertIsInstance(f, Callable[[], None]) 471 with self.assertRaises(TypeError): 472 self.assertIsInstance(f, Callable[[], Any]) 473 with self.assertRaises(TypeError): 474 self.assertNotIsInstance(None, Callable[[], None]) 475 with self.assertRaises(TypeError): 476 self.assertNotIsInstance(None, Callable[[], Any]) 477 478 def test_repr(self): 479 ct0 = Callable[[], bool] 480 self.assertEqual(repr(ct0), 'typing.Callable[[], bool]') 481 ct2 = Callable[[str, float], int] 482 self.assertEqual(repr(ct2), 'typing.Callable[[str, float], int]') 483 ctv = Callable[..., str] 484 self.assertEqual(repr(ctv), 'typing.Callable[..., str]') 485 486 def test_callable_with_ellipsis(self): 487 488 def foo(a: Callable[..., T]): 489 pass 490 491 self.assertEqual(get_type_hints(foo, globals(), locals()), 492 {'a': Callable[..., T]}) 493 494 def test_ellipsis_in_generic(self): 495 # Shouldn't crash; see https://github.com/python/typing/issues/259 496 typing.List[Callable[..., str]] 497 498 499XK = TypeVar('XK', str, bytes) 500XV = TypeVar('XV') 501 502 503class SimpleMapping(Generic[XK, XV]): 504 505 def __getitem__(self, key: XK) -> XV: 506 ... 507 508 def __setitem__(self, key: XK, value: XV): 509 ... 510 511 def get(self, key: XK, default: XV = None) -> XV: 512 ... 513 514 515class MySimpleMapping(SimpleMapping[XK, XV]): 516 517 def __init__(self): 518 self.store = {} 519 520 def __getitem__(self, key: str): 521 return self.store[key] 522 523 def __setitem__(self, key: str, value): 524 self.store[key] = value 525 526 def get(self, key: str, default=None): 527 try: 528 return self.store[key] 529 except KeyError: 530 return default 531 532 533class ProtocolTests(BaseTestCase): 534 535 def test_supports_int(self): 536 self.assertIsSubclass(int, typing.SupportsInt) 537 self.assertNotIsSubclass(str, typing.SupportsInt) 538 539 def test_supports_float(self): 540 self.assertIsSubclass(float, typing.SupportsFloat) 541 self.assertNotIsSubclass(str, typing.SupportsFloat) 542 543 def test_supports_complex(self): 544 545 # Note: complex itself doesn't have __complex__. 546 class C: 547 def __complex__(self): 548 return 0j 549 550 self.assertIsSubclass(C, typing.SupportsComplex) 551 self.assertNotIsSubclass(str, typing.SupportsComplex) 552 553 def test_supports_bytes(self): 554 555 # Note: bytes itself doesn't have __bytes__. 556 class B: 557 def __bytes__(self): 558 return b'' 559 560 self.assertIsSubclass(B, typing.SupportsBytes) 561 self.assertNotIsSubclass(str, typing.SupportsBytes) 562 563 def test_supports_abs(self): 564 self.assertIsSubclass(float, typing.SupportsAbs) 565 self.assertIsSubclass(int, typing.SupportsAbs) 566 self.assertNotIsSubclass(str, typing.SupportsAbs) 567 568 def test_supports_round(self): 569 issubclass(float, typing.SupportsRound) 570 self.assertIsSubclass(float, typing.SupportsRound) 571 self.assertIsSubclass(int, typing.SupportsRound) 572 self.assertNotIsSubclass(str, typing.SupportsRound) 573 574 def test_reversible(self): 575 self.assertIsSubclass(list, typing.Reversible) 576 self.assertNotIsSubclass(int, typing.Reversible) 577 578 def test_protocol_instance_type_error(self): 579 with self.assertRaises(TypeError): 580 isinstance(0, typing.SupportsAbs) 581 class C1(typing.SupportsInt): 582 def __int__(self) -> int: 583 return 42 584 class C2(C1): 585 pass 586 c = C2() 587 self.assertIsInstance(c, C1) 588 589 590class GenericTests(BaseTestCase): 591 592 def test_basics(self): 593 X = SimpleMapping[str, Any] 594 self.assertEqual(X.__parameters__, ()) 595 with self.assertRaises(TypeError): 596 X[str] 597 with self.assertRaises(TypeError): 598 X[str, str] 599 Y = SimpleMapping[XK, str] 600 self.assertEqual(Y.__parameters__, (XK,)) 601 Y[str] 602 with self.assertRaises(TypeError): 603 Y[str, str] 604 SM1 = SimpleMapping[str, int] 605 with self.assertRaises(TypeError): 606 issubclass(SM1, SimpleMapping) 607 self.assertIsInstance(SM1(), SimpleMapping) 608 609 def test_generic_errors(self): 610 T = TypeVar('T') 611 S = TypeVar('S') 612 with self.assertRaises(TypeError): 613 Generic[T]() 614 with self.assertRaises(TypeError): 615 Generic[T][T] 616 with self.assertRaises(TypeError): 617 Generic[T][S] 618 with self.assertRaises(TypeError): 619 class C(Generic[T], Generic[T]): ... 620 with self.assertRaises(TypeError): 621 isinstance([], List[int]) 622 with self.assertRaises(TypeError): 623 issubclass(list, List[int]) 624 with self.assertRaises(TypeError): 625 class NewGeneric(Generic): ... 626 with self.assertRaises(TypeError): 627 class MyGeneric(Generic[T], Generic[S]): ... 628 with self.assertRaises(TypeError): 629 class MyGeneric(List[T], Generic[S]): ... 630 631 def test_init(self): 632 T = TypeVar('T') 633 S = TypeVar('S') 634 with self.assertRaises(TypeError): 635 Generic[T, T] 636 with self.assertRaises(TypeError): 637 Generic[T, S, T] 638 639 def test_init_subclass(self): 640 class X(typing.Generic[T]): 641 def __init_subclass__(cls, **kwargs): 642 super().__init_subclass__(**kwargs) 643 cls.attr = 42 644 class Y(X): 645 pass 646 self.assertEqual(Y.attr, 42) 647 with self.assertRaises(AttributeError): 648 X.attr 649 X.attr = 1 650 Y.attr = 2 651 class Z(Y): 652 pass 653 class W(X[int]): 654 pass 655 self.assertEqual(Y.attr, 2) 656 self.assertEqual(Z.attr, 42) 657 self.assertEqual(W.attr, 42) 658 659 def test_repr(self): 660 self.assertEqual(repr(SimpleMapping), 661 f"<class '{__name__}.SimpleMapping'>") 662 self.assertEqual(repr(MySimpleMapping), 663 f"<class '{__name__}.MySimpleMapping'>") 664 665 def test_chain_repr(self): 666 T = TypeVar('T') 667 S = TypeVar('S') 668 669 class C(Generic[T]): 670 pass 671 672 X = C[Tuple[S, T]] 673 self.assertEqual(X, C[Tuple[S, T]]) 674 self.assertNotEqual(X, C[Tuple[T, S]]) 675 676 Y = X[T, int] 677 self.assertEqual(Y, X[T, int]) 678 self.assertNotEqual(Y, X[S, int]) 679 self.assertNotEqual(Y, X[T, str]) 680 681 Z = Y[str] 682 self.assertEqual(Z, Y[str]) 683 self.assertNotEqual(Z, Y[int]) 684 self.assertNotEqual(Z, Y[T]) 685 686 self.assertTrue(str(Z).endswith( 687 '.C[typing.Tuple[str, int]]')) 688 689 def test_new_repr(self): 690 T = TypeVar('T') 691 U = TypeVar('U', covariant=True) 692 S = TypeVar('S') 693 694 self.assertEqual(repr(List), 'typing.List') 695 self.assertEqual(repr(List[T]), 'typing.List[~T]') 696 self.assertEqual(repr(List[U]), 'typing.List[+U]') 697 self.assertEqual(repr(List[S][T][int]), 'typing.List[int]') 698 self.assertEqual(repr(List[int]), 'typing.List[int]') 699 700 def test_new_repr_complex(self): 701 T = TypeVar('T') 702 TS = TypeVar('TS') 703 704 self.assertEqual(repr(typing.Mapping[T, TS][TS, T]), 'typing.Mapping[~TS, ~T]') 705 self.assertEqual(repr(List[Tuple[T, TS]][int, T]), 706 'typing.List[typing.Tuple[int, ~T]]') 707 self.assertEqual( 708 repr(List[Tuple[T, T]][List[int]]), 709 'typing.List[typing.Tuple[typing.List[int], typing.List[int]]]' 710 ) 711 712 def test_new_repr_bare(self): 713 T = TypeVar('T') 714 self.assertEqual(repr(Generic[T]), 'typing.Generic[~T]') 715 self.assertEqual(repr(typing._Protocol[T]), 'typing._Protocol[~T]') 716 class C(typing.Dict[Any, Any]): ... 717 # this line should just work 718 repr(C.__mro__) 719 720 def test_dict(self): 721 T = TypeVar('T') 722 723 class B(Generic[T]): 724 pass 725 726 b = B() 727 b.foo = 42 728 self.assertEqual(b.__dict__, {'foo': 42}) 729 730 class C(B[int]): 731 pass 732 733 c = C() 734 c.bar = 'abc' 735 self.assertEqual(c.__dict__, {'bar': 'abc'}) 736 737 def test_subscripted_generics_as_proxies(self): 738 T = TypeVar('T') 739 class C(Generic[T]): 740 x = 'def' 741 self.assertEqual(C[int].x, 'def') 742 self.assertEqual(C[C[int]].x, 'def') 743 C[C[int]].x = 'changed' 744 self.assertEqual(C.x, 'changed') 745 self.assertEqual(C[str].x, 'changed') 746 C[List[str]].z = 'new' 747 self.assertEqual(C.z, 'new') 748 self.assertEqual(C[Tuple[int]].z, 'new') 749 750 self.assertEqual(C().x, 'changed') 751 self.assertEqual(C[Tuple[str]]().z, 'new') 752 753 class D(C[T]): 754 pass 755 self.assertEqual(D[int].x, 'changed') 756 self.assertEqual(D.z, 'new') 757 D.z = 'from derived z' 758 D[int].x = 'from derived x' 759 self.assertEqual(C.x, 'changed') 760 self.assertEqual(C[int].z, 'new') 761 self.assertEqual(D.x, 'from derived x') 762 self.assertEqual(D[str].z, 'from derived z') 763 764 def test_abc_registry_kept(self): 765 T = TypeVar('T') 766 class C(collections.abc.Mapping, Generic[T]): ... 767 C.register(int) 768 self.assertIsInstance(1, C) 769 C[int] 770 self.assertIsInstance(1, C) 771 C._abc_registry_clear() 772 C._abc_caches_clear() # To keep refleak hunting mode clean 773 774 def test_false_subclasses(self): 775 class MyMapping(MutableMapping[str, str]): pass 776 self.assertNotIsInstance({}, MyMapping) 777 self.assertNotIsSubclass(dict, MyMapping) 778 779 def test_abc_bases(self): 780 class MM(MutableMapping[str, str]): 781 def __getitem__(self, k): 782 return None 783 def __setitem__(self, k, v): 784 pass 785 def __delitem__(self, k): 786 pass 787 def __iter__(self): 788 return iter(()) 789 def __len__(self): 790 return 0 791 # this should just work 792 MM().update() 793 self.assertIsInstance(MM(), collections.abc.MutableMapping) 794 self.assertIsInstance(MM(), MutableMapping) 795 self.assertNotIsInstance(MM(), List) 796 self.assertNotIsInstance({}, MM) 797 798 def test_multiple_bases(self): 799 class MM1(MutableMapping[str, str], collections.abc.MutableMapping): 800 pass 801 class MM2(collections.abc.MutableMapping, MutableMapping[str, str]): 802 pass 803 self.assertEqual(MM2.__bases__, (collections.abc.MutableMapping, Generic)) 804 805 def test_orig_bases(self): 806 T = TypeVar('T') 807 class C(typing.Dict[str, T]): ... 808 self.assertEqual(C.__orig_bases__, (typing.Dict[str, T],)) 809 810 def test_naive_runtime_checks(self): 811 def naive_dict_check(obj, tp): 812 # Check if a dictionary conforms to Dict type 813 if len(tp.__parameters__) > 0: 814 raise NotImplementedError 815 if tp.__args__: 816 KT, VT = tp.__args__ 817 return all( 818 isinstance(k, KT) and isinstance(v, VT) 819 for k, v in obj.items() 820 ) 821 self.assertTrue(naive_dict_check({'x': 1}, typing.Dict[str, int])) 822 self.assertFalse(naive_dict_check({1: 'x'}, typing.Dict[str, int])) 823 with self.assertRaises(NotImplementedError): 824 naive_dict_check({1: 'x'}, typing.Dict[str, T]) 825 826 def naive_generic_check(obj, tp): 827 # Check if an instance conforms to the generic class 828 if not hasattr(obj, '__orig_class__'): 829 raise NotImplementedError 830 return obj.__orig_class__ == tp 831 class Node(Generic[T]): ... 832 self.assertTrue(naive_generic_check(Node[int](), Node[int])) 833 self.assertFalse(naive_generic_check(Node[str](), Node[int])) 834 self.assertFalse(naive_generic_check(Node[str](), List)) 835 with self.assertRaises(NotImplementedError): 836 naive_generic_check([1, 2, 3], Node[int]) 837 838 def naive_list_base_check(obj, tp): 839 # Check if list conforms to a List subclass 840 return all(isinstance(x, tp.__orig_bases__[0].__args__[0]) 841 for x in obj) 842 class C(List[int]): ... 843 self.assertTrue(naive_list_base_check([1, 2, 3], C)) 844 self.assertFalse(naive_list_base_check(['a', 'b'], C)) 845 846 def test_multi_subscr_base(self): 847 T = TypeVar('T') 848 U = TypeVar('U') 849 V = TypeVar('V') 850 class C(List[T][U][V]): ... 851 class D(C, List[T][U][V]): ... 852 self.assertEqual(C.__parameters__, (V,)) 853 self.assertEqual(D.__parameters__, (V,)) 854 self.assertEqual(C[int].__parameters__, ()) 855 self.assertEqual(D[int].__parameters__, ()) 856 self.assertEqual(C[int].__args__, (int,)) 857 self.assertEqual(D[int].__args__, (int,)) 858 self.assertEqual(C.__bases__, (list, Generic)) 859 self.assertEqual(D.__bases__, (C, list, Generic)) 860 self.assertEqual(C.__orig_bases__, (List[T][U][V],)) 861 self.assertEqual(D.__orig_bases__, (C, List[T][U][V])) 862 863 def test_subscript_meta(self): 864 T = TypeVar('T') 865 class Meta(type): ... 866 self.assertEqual(Type[Meta], Type[Meta]) 867 self.assertEqual(Union[T, int][Meta], Union[Meta, int]) 868 self.assertEqual(Callable[..., Meta].__args__, (Ellipsis, Meta)) 869 870 def test_generic_hashes(self): 871 class A(Generic[T]): 872 ... 873 874 class B(Generic[T]): 875 class A(Generic[T]): 876 ... 877 878 self.assertEqual(A, A) 879 self.assertEqual(mod_generics_cache.A[str], mod_generics_cache.A[str]) 880 self.assertEqual(B.A, B.A) 881 self.assertEqual(mod_generics_cache.B.A[B.A[str]], 882 mod_generics_cache.B.A[B.A[str]]) 883 884 self.assertNotEqual(A, B.A) 885 self.assertNotEqual(A, mod_generics_cache.A) 886 self.assertNotEqual(A, mod_generics_cache.B.A) 887 self.assertNotEqual(B.A, mod_generics_cache.A) 888 self.assertNotEqual(B.A, mod_generics_cache.B.A) 889 890 self.assertNotEqual(A[str], B.A[str]) 891 self.assertNotEqual(A[List[Any]], B.A[List[Any]]) 892 self.assertNotEqual(A[str], mod_generics_cache.A[str]) 893 self.assertNotEqual(A[str], mod_generics_cache.B.A[str]) 894 self.assertNotEqual(B.A[int], mod_generics_cache.A[int]) 895 self.assertNotEqual(B.A[List[Any]], mod_generics_cache.B.A[List[Any]]) 896 897 self.assertNotEqual(Tuple[A[str]], Tuple[B.A[str]]) 898 self.assertNotEqual(Tuple[A[List[Any]]], Tuple[B.A[List[Any]]]) 899 self.assertNotEqual(Union[str, A[str]], Union[str, mod_generics_cache.A[str]]) 900 self.assertNotEqual(Union[A[str], A[str]], 901 Union[A[str], mod_generics_cache.A[str]]) 902 self.assertNotEqual(typing.FrozenSet[A[str]], 903 typing.FrozenSet[mod_generics_cache.B.A[str]]) 904 905 if sys.version_info[:2] > (3, 2): 906 self.assertTrue(repr(Tuple[A[str]]).endswith('<locals>.A[str]]')) 907 self.assertTrue(repr(Tuple[B.A[str]]).endswith('<locals>.B.A[str]]')) 908 self.assertTrue(repr(Tuple[mod_generics_cache.A[str]]) 909 .endswith('mod_generics_cache.A[str]]')) 910 self.assertTrue(repr(Tuple[mod_generics_cache.B.A[str]]) 911 .endswith('mod_generics_cache.B.A[str]]')) 912 913 def test_extended_generic_rules_eq(self): 914 T = TypeVar('T') 915 U = TypeVar('U') 916 self.assertEqual(Tuple[T, T][int], Tuple[int, int]) 917 self.assertEqual(typing.Iterable[Tuple[T, T]][T], typing.Iterable[Tuple[T, T]]) 918 with self.assertRaises(TypeError): 919 Tuple[T, int][()] 920 with self.assertRaises(TypeError): 921 Tuple[T, U][T, ...] 922 923 self.assertEqual(Union[T, int][int], int) 924 self.assertEqual(Union[T, U][int, Union[int, str]], Union[int, str]) 925 class Base: ... 926 class Derived(Base): ... 927 self.assertEqual(Union[T, Base][Union[Base, Derived]], Union[Base, Derived]) 928 with self.assertRaises(TypeError): 929 Union[T, int][1] 930 931 self.assertEqual(Callable[[T], T][KT], Callable[[KT], KT]) 932 self.assertEqual(Callable[..., List[T]][int], Callable[..., List[int]]) 933 with self.assertRaises(TypeError): 934 Callable[[T], U][..., int] 935 with self.assertRaises(TypeError): 936 Callable[[T], U][[], int] 937 938 def test_extended_generic_rules_repr(self): 939 T = TypeVar('T') 940 self.assertEqual(repr(Union[Tuple, Callable]).replace('typing.', ''), 941 'Union[Tuple, Callable]') 942 self.assertEqual(repr(Union[Tuple, Tuple[int]]).replace('typing.', ''), 943 'Union[Tuple, Tuple[int]]') 944 self.assertEqual(repr(Callable[..., Optional[T]][int]).replace('typing.', ''), 945 'Callable[..., Union[int, NoneType]]') 946 self.assertEqual(repr(Callable[[], List[T]][int]).replace('typing.', ''), 947 'Callable[[], List[int]]') 948 949 def test_generic_forward_ref(self): 950 def foobar(x: List[List['CC']]): ... 951 class CC: ... 952 self.assertEqual( 953 get_type_hints(foobar, globals(), locals()), 954 {'x': List[List[CC]]} 955 ) 956 T = TypeVar('T') 957 AT = Tuple[T, ...] 958 def barfoo(x: AT): ... 959 self.assertIs(get_type_hints(barfoo, globals(), locals())['x'], AT) 960 CT = Callable[..., List[T]] 961 def barfoo2(x: CT): ... 962 self.assertIs(get_type_hints(barfoo2, globals(), locals())['x'], CT) 963 964 def test_extended_generic_rules_subclassing(self): 965 class T1(Tuple[T, KT]): ... 966 class T2(Tuple[T, ...]): ... 967 class C1(Callable[[T], T]): ... 968 class C2(Callable[..., int]): 969 def __call__(self): 970 return None 971 972 self.assertEqual(T1.__parameters__, (T, KT)) 973 self.assertEqual(T1[int, str].__args__, (int, str)) 974 self.assertEqual(T1[int, T].__origin__, T1) 975 976 self.assertEqual(T2.__parameters__, (T,)) 977 with self.assertRaises(TypeError): 978 T1[int] 979 with self.assertRaises(TypeError): 980 T2[int, str] 981 982 self.assertEqual(repr(C1[int]).split('.')[-1], 'C1[int]') 983 self.assertEqual(C2.__parameters__, ()) 984 self.assertIsInstance(C2(), collections.abc.Callable) 985 self.assertIsSubclass(C2, collections.abc.Callable) 986 self.assertIsSubclass(C1, collections.abc.Callable) 987 self.assertIsInstance(T1(), tuple) 988 self.assertIsSubclass(T2, tuple) 989 with self.assertRaises(TypeError): 990 issubclass(Tuple[int, ...], typing.Sequence) 991 with self.assertRaises(TypeError): 992 issubclass(Tuple[int, ...], typing.Iterable) 993 994 def test_fail_with_bare_union(self): 995 with self.assertRaises(TypeError): 996 List[Union] 997 with self.assertRaises(TypeError): 998 Tuple[Optional] 999 with self.assertRaises(TypeError): 1000 ClassVar[ClassVar] 1001 with self.assertRaises(TypeError): 1002 List[ClassVar[int]] 1003 1004 def test_fail_with_bare_generic(self): 1005 T = TypeVar('T') 1006 with self.assertRaises(TypeError): 1007 List[Generic] 1008 with self.assertRaises(TypeError): 1009 Tuple[Generic[T]] 1010 with self.assertRaises(TypeError): 1011 List[typing._Protocol] 1012 1013 def test_type_erasure_special(self): 1014 T = TypeVar('T') 1015 # this is the only test that checks type caching 1016 self.clear_caches() 1017 class MyTup(Tuple[T, T]): ... 1018 self.assertIs(MyTup[int]().__class__, MyTup) 1019 self.assertIs(MyTup[int]().__orig_class__, MyTup[int]) 1020 class MyCall(Callable[..., T]): 1021 def __call__(self): return None 1022 self.assertIs(MyCall[T]().__class__, MyCall) 1023 self.assertIs(MyCall[T]().__orig_class__, MyCall[T]) 1024 class MyDict(typing.Dict[T, T]): ... 1025 self.assertIs(MyDict[int]().__class__, MyDict) 1026 self.assertIs(MyDict[int]().__orig_class__, MyDict[int]) 1027 class MyDef(typing.DefaultDict[str, T]): ... 1028 self.assertIs(MyDef[int]().__class__, MyDef) 1029 self.assertIs(MyDef[int]().__orig_class__, MyDef[int]) 1030 # ChainMap was added in 3.3 1031 if sys.version_info >= (3, 3): 1032 class MyChain(typing.ChainMap[str, T]): ... 1033 self.assertIs(MyChain[int]().__class__, MyChain) 1034 self.assertIs(MyChain[int]().__orig_class__, MyChain[int]) 1035 1036 def test_all_repr_eq_any(self): 1037 objs = (getattr(typing, el) for el in typing.__all__) 1038 for obj in objs: 1039 self.assertNotEqual(repr(obj), '') 1040 self.assertEqual(obj, obj) 1041 if getattr(obj, '__parameters__', None) and len(obj.__parameters__) == 1: 1042 self.assertEqual(obj[Any].__args__, (Any,)) 1043 if isinstance(obj, type): 1044 for base in obj.__mro__: 1045 self.assertNotEqual(repr(base), '') 1046 self.assertEqual(base, base) 1047 1048 def test_pickle(self): 1049 global C # pickle wants to reference the class by name 1050 T = TypeVar('T') 1051 1052 class B(Generic[T]): 1053 pass 1054 1055 class C(B[int]): 1056 pass 1057 1058 c = C() 1059 c.foo = 42 1060 c.bar = 'abc' 1061 for proto in range(pickle.HIGHEST_PROTOCOL + 1): 1062 z = pickle.dumps(c, proto) 1063 x = pickle.loads(z) 1064 self.assertEqual(x.foo, 42) 1065 self.assertEqual(x.bar, 'abc') 1066 self.assertEqual(x.__dict__, {'foo': 42, 'bar': 'abc'}) 1067 samples = [Any, Union, Tuple, Callable, ClassVar, 1068 Union[int, str], ClassVar[List], Tuple[int, ...], Callable[[str], bytes], 1069 typing.DefaultDict, typing.FrozenSet[int]] 1070 for s in samples: 1071 for proto in range(pickle.HIGHEST_PROTOCOL + 1): 1072 z = pickle.dumps(s, proto) 1073 x = pickle.loads(z) 1074 self.assertEqual(s, x) 1075 more_samples = [List, typing.Iterable, typing.Type, List[int], 1076 typing.Type[typing.Mapping], typing.AbstractSet[Tuple[int, str]]] 1077 for s in more_samples: 1078 for proto in range(pickle.HIGHEST_PROTOCOL + 1): 1079 z = pickle.dumps(s, proto) 1080 x = pickle.loads(z) 1081 self.assertEqual(s, x) 1082 1083 def test_copy_and_deepcopy(self): 1084 T = TypeVar('T') 1085 class Node(Generic[T]): ... 1086 things = [Union[T, int], Tuple[T, int], Callable[..., T], Callable[[int], int], 1087 Tuple[Any, Any], Node[T], Node[int], Node[Any], typing.Iterable[T], 1088 typing.Iterable[Any], typing.Iterable[int], typing.Dict[int, str], 1089 typing.Dict[T, Any], ClassVar[int], ClassVar[List[T]], Tuple['T', 'T'], 1090 Union['T', int], List['T'], typing.Mapping['T', int]] 1091 for t in things + [Any]: 1092 self.assertEqual(t, copy(t)) 1093 self.assertEqual(t, deepcopy(t)) 1094 1095 def test_immutability_by_copy_and_pickle(self): 1096 # Special forms like Union, Any, etc., generic aliases to containers like List, 1097 # Mapping, etc., and type variabcles are considered immutable by copy and pickle. 1098 global TP, TPB, TPV # for pickle 1099 TP = TypeVar('TP') 1100 TPB = TypeVar('TPB', bound=int) 1101 TPV = TypeVar('TPV', bytes, str) 1102 for X in [TP, TPB, TPV, List, typing.Mapping, ClassVar, typing.Iterable, 1103 Union, Any, Tuple, Callable]: 1104 self.assertIs(copy(X), X) 1105 self.assertIs(deepcopy(X), X) 1106 self.assertIs(pickle.loads(pickle.dumps(X)), X) 1107 # Check that local type variables are copyable. 1108 TL = TypeVar('TL') 1109 TLB = TypeVar('TLB', bound=int) 1110 TLV = TypeVar('TLV', bytes, str) 1111 for X in [TL, TLB, TLV]: 1112 self.assertIs(copy(X), X) 1113 self.assertIs(deepcopy(X), X) 1114 1115 def test_copy_generic_instances(self): 1116 T = TypeVar('T') 1117 class C(Generic[T]): 1118 def __init__(self, attr: T) -> None: 1119 self.attr = attr 1120 1121 c = C(42) 1122 self.assertEqual(copy(c).attr, 42) 1123 self.assertEqual(deepcopy(c).attr, 42) 1124 self.assertIsNot(copy(c), c) 1125 self.assertIsNot(deepcopy(c), c) 1126 c.attr = 1 1127 self.assertEqual(copy(c).attr, 1) 1128 self.assertEqual(deepcopy(c).attr, 1) 1129 ci = C[int](42) 1130 self.assertEqual(copy(ci).attr, 42) 1131 self.assertEqual(deepcopy(ci).attr, 42) 1132 self.assertIsNot(copy(ci), ci) 1133 self.assertIsNot(deepcopy(ci), ci) 1134 ci.attr = 1 1135 self.assertEqual(copy(ci).attr, 1) 1136 self.assertEqual(deepcopy(ci).attr, 1) 1137 self.assertEqual(ci.__orig_class__, C[int]) 1138 1139 def test_weakref_all(self): 1140 T = TypeVar('T') 1141 things = [Any, Union[T, int], Callable[..., T], Tuple[Any, Any], 1142 Optional[List[int]], typing.Mapping[int, str], 1143 typing.re.Match[bytes], typing.Iterable['whatever']] 1144 for t in things: 1145 self.assertEqual(weakref.ref(t)(), t) 1146 1147 def test_parameterized_slots(self): 1148 T = TypeVar('T') 1149 class C(Generic[T]): 1150 __slots__ = ('potato',) 1151 1152 c = C() 1153 c_int = C[int]() 1154 1155 c.potato = 0 1156 c_int.potato = 0 1157 with self.assertRaises(AttributeError): 1158 c.tomato = 0 1159 with self.assertRaises(AttributeError): 1160 c_int.tomato = 0 1161 1162 def foo(x: C['C']): ... 1163 self.assertEqual(get_type_hints(foo, globals(), locals())['x'], C[C]) 1164 self.assertEqual(copy(C[int]), deepcopy(C[int])) 1165 1166 def test_parameterized_slots_dict(self): 1167 T = TypeVar('T') 1168 class D(Generic[T]): 1169 __slots__ = {'banana': 42} 1170 1171 d = D() 1172 d_int = D[int]() 1173 1174 d.banana = 'yes' 1175 d_int.banana = 'yes' 1176 with self.assertRaises(AttributeError): 1177 d.foobar = 'no' 1178 with self.assertRaises(AttributeError): 1179 d_int.foobar = 'no' 1180 1181 def test_errors(self): 1182 with self.assertRaises(TypeError): 1183 B = SimpleMapping[XK, Any] 1184 1185 class C(Generic[B]): 1186 pass 1187 1188 def test_repr_2(self): 1189 class C(Generic[T]): 1190 pass 1191 1192 self.assertEqual(C.__module__, __name__) 1193 self.assertEqual(C.__qualname__, 1194 'GenericTests.test_repr_2.<locals>.C') 1195 X = C[int] 1196 self.assertEqual(X.__module__, __name__) 1197 self.assertEqual(repr(X).split('.')[-1], 'C[int]') 1198 1199 class Y(C[int]): 1200 pass 1201 1202 self.assertEqual(Y.__module__, __name__) 1203 self.assertEqual(Y.__qualname__, 1204 'GenericTests.test_repr_2.<locals>.Y') 1205 1206 def test_eq_1(self): 1207 self.assertEqual(Generic, Generic) 1208 self.assertEqual(Generic[T], Generic[T]) 1209 self.assertNotEqual(Generic[KT], Generic[VT]) 1210 1211 def test_eq_2(self): 1212 1213 class A(Generic[T]): 1214 pass 1215 1216 class B(Generic[T]): 1217 pass 1218 1219 self.assertEqual(A, A) 1220 self.assertNotEqual(A, B) 1221 self.assertEqual(A[T], A[T]) 1222 self.assertNotEqual(A[T], B[T]) 1223 1224 def test_multiple_inheritance(self): 1225 1226 class A(Generic[T, VT]): 1227 pass 1228 1229 class B(Generic[KT, T]): 1230 pass 1231 1232 class C(A[T, VT], Generic[VT, T, KT], B[KT, T]): 1233 pass 1234 1235 self.assertEqual(C.__parameters__, (VT, T, KT)) 1236 1237 def test_multiple_inheritance_special(self): 1238 S = TypeVar('S') 1239 class B(Generic[S]): ... 1240 class C(List[int], B): ... 1241 self.assertEqual(C.__mro__, (C, list, B, Generic, object)) 1242 1243 def test_init_subclass_super_called(self): 1244 class FinalException(Exception): 1245 pass 1246 1247 class Final: 1248 def __init_subclass__(cls, **kwargs) -> None: 1249 for base in cls.__bases__: 1250 if base is not Final and issubclass(base, Final): 1251 raise FinalException(base) 1252 super().__init_subclass__(**kwargs) 1253 class Test(Generic[T], Final): 1254 pass 1255 with self.assertRaises(FinalException): 1256 class Subclass(Test): 1257 pass 1258 with self.assertRaises(FinalException): 1259 class Subclass(Test[int]): 1260 pass 1261 1262 def test_nested(self): 1263 1264 G = Generic 1265 1266 class Visitor(G[T]): 1267 1268 a = None 1269 1270 def set(self, a: T): 1271 self.a = a 1272 1273 def get(self): 1274 return self.a 1275 1276 def visit(self) -> T: 1277 return self.a 1278 1279 V = Visitor[typing.List[int]] 1280 1281 class IntListVisitor(V): 1282 1283 def append(self, x: int): 1284 self.a.append(x) 1285 1286 a = IntListVisitor() 1287 a.set([]) 1288 a.append(1) 1289 a.append(42) 1290 self.assertEqual(a.get(), [1, 42]) 1291 1292 def test_type_erasure(self): 1293 T = TypeVar('T') 1294 1295 class Node(Generic[T]): 1296 def __init__(self, label: T, 1297 left: 'Node[T]' = None, 1298 right: 'Node[T]' = None): 1299 self.label = label # type: T 1300 self.left = left # type: Optional[Node[T]] 1301 self.right = right # type: Optional[Node[T]] 1302 1303 def foo(x: T): 1304 a = Node(x) 1305 b = Node[T](x) 1306 c = Node[Any](x) 1307 self.assertIs(type(a), Node) 1308 self.assertIs(type(b), Node) 1309 self.assertIs(type(c), Node) 1310 self.assertEqual(a.label, x) 1311 self.assertEqual(b.label, x) 1312 self.assertEqual(c.label, x) 1313 1314 foo(42) 1315 1316 def test_implicit_any(self): 1317 T = TypeVar('T') 1318 1319 class C(Generic[T]): 1320 pass 1321 1322 class D(C): 1323 pass 1324 1325 self.assertEqual(D.__parameters__, ()) 1326 1327 with self.assertRaises(Exception): 1328 D[int] 1329 with self.assertRaises(Exception): 1330 D[Any] 1331 with self.assertRaises(Exception): 1332 D[T] 1333 1334 def test_new_with_args(self): 1335 1336 class A(Generic[T]): 1337 pass 1338 1339 class B: 1340 def __new__(cls, arg): 1341 # call object 1342 obj = super().__new__(cls) 1343 obj.arg = arg 1344 return obj 1345 1346 # mro: C, A, Generic, B, object 1347 class C(A, B): 1348 pass 1349 1350 c = C('foo') 1351 self.assertEqual(c.arg, 'foo') 1352 1353 def test_new_with_args2(self): 1354 1355 class A: 1356 def __init__(self, arg): 1357 self.from_a = arg 1358 # call object 1359 super().__init__() 1360 1361 # mro: C, Generic, A, object 1362 class C(Generic[T], A): 1363 def __init__(self, arg): 1364 self.from_c = arg 1365 # call Generic 1366 super().__init__(arg) 1367 1368 c = C('foo') 1369 self.assertEqual(c.from_a, 'foo') 1370 self.assertEqual(c.from_c, 'foo') 1371 1372 def test_new_no_args(self): 1373 1374 class A(Generic[T]): 1375 pass 1376 1377 with self.assertRaises(TypeError): 1378 A('foo') 1379 1380 class B: 1381 def __new__(cls): 1382 # call object 1383 obj = super().__new__(cls) 1384 obj.from_b = 'b' 1385 return obj 1386 1387 # mro: C, A, Generic, B, object 1388 class C(A, B): 1389 def __init__(self, arg): 1390 self.arg = arg 1391 1392 def __new__(cls, arg): 1393 # call A 1394 obj = super().__new__(cls) 1395 obj.from_c = 'c' 1396 return obj 1397 1398 c = C('foo') 1399 self.assertEqual(c.arg, 'foo') 1400 self.assertEqual(c.from_b, 'b') 1401 self.assertEqual(c.from_c, 'c') 1402 1403 1404class ClassVarTests(BaseTestCase): 1405 1406 def test_basics(self): 1407 with self.assertRaises(TypeError): 1408 ClassVar[1] 1409 with self.assertRaises(TypeError): 1410 ClassVar[int, str] 1411 with self.assertRaises(TypeError): 1412 ClassVar[int][str] 1413 1414 def test_repr(self): 1415 self.assertEqual(repr(ClassVar), 'typing.ClassVar') 1416 cv = ClassVar[int] 1417 self.assertEqual(repr(cv), 'typing.ClassVar[int]') 1418 cv = ClassVar[Employee] 1419 self.assertEqual(repr(cv), 'typing.ClassVar[%s.Employee]' % __name__) 1420 1421 def test_cannot_subclass(self): 1422 with self.assertRaises(TypeError): 1423 class C(type(ClassVar)): 1424 pass 1425 with self.assertRaises(TypeError): 1426 class C(type(ClassVar[int])): 1427 pass 1428 1429 def test_cannot_init(self): 1430 with self.assertRaises(TypeError): 1431 ClassVar() 1432 with self.assertRaises(TypeError): 1433 type(ClassVar)() 1434 with self.assertRaises(TypeError): 1435 type(ClassVar[Optional[int]])() 1436 1437 def test_no_isinstance(self): 1438 with self.assertRaises(TypeError): 1439 isinstance(1, ClassVar[int]) 1440 with self.assertRaises(TypeError): 1441 issubclass(int, ClassVar) 1442 1443 1444class CastTests(BaseTestCase): 1445 1446 def test_basics(self): 1447 self.assertEqual(cast(int, 42), 42) 1448 self.assertEqual(cast(float, 42), 42) 1449 self.assertIs(type(cast(float, 42)), int) 1450 self.assertEqual(cast(Any, 42), 42) 1451 self.assertEqual(cast(list, 42), 42) 1452 self.assertEqual(cast(Union[str, float], 42), 42) 1453 self.assertEqual(cast(AnyStr, 42), 42) 1454 self.assertEqual(cast(None, 42), 42) 1455 1456 def test_errors(self): 1457 # Bogus calls are not expected to fail. 1458 cast(42, 42) 1459 cast('hello', 42) 1460 1461 1462class ForwardRefTests(BaseTestCase): 1463 1464 def test_basics(self): 1465 1466 class Node(Generic[T]): 1467 1468 def __init__(self, label: T): 1469 self.label = label 1470 self.left = self.right = None 1471 1472 def add_both(self, 1473 left: 'Optional[Node[T]]', 1474 right: 'Node[T]' = None, 1475 stuff: int = None, 1476 blah=None): 1477 self.left = left 1478 self.right = right 1479 1480 def add_left(self, node: Optional['Node[T]']): 1481 self.add_both(node, None) 1482 1483 def add_right(self, node: 'Node[T]' = None): 1484 self.add_both(None, node) 1485 1486 t = Node[int] 1487 both_hints = get_type_hints(t.add_both, globals(), locals()) 1488 self.assertEqual(both_hints['left'], Optional[Node[T]]) 1489 self.assertEqual(both_hints['right'], Optional[Node[T]]) 1490 self.assertEqual(both_hints['left'], both_hints['right']) 1491 self.assertEqual(both_hints['stuff'], Optional[int]) 1492 self.assertNotIn('blah', both_hints) 1493 1494 left_hints = get_type_hints(t.add_left, globals(), locals()) 1495 self.assertEqual(left_hints['node'], Optional[Node[T]]) 1496 1497 right_hints = get_type_hints(t.add_right, globals(), locals()) 1498 self.assertEqual(right_hints['node'], Optional[Node[T]]) 1499 1500 def test_forwardref_instance_type_error(self): 1501 fr = typing.ForwardRef('int') 1502 with self.assertRaises(TypeError): 1503 isinstance(42, fr) 1504 1505 def test_forwardref_subclass_type_error(self): 1506 fr = typing.ForwardRef('int') 1507 with self.assertRaises(TypeError): 1508 issubclass(int, fr) 1509 1510 def test_forward_equality(self): 1511 fr = typing.ForwardRef('int') 1512 self.assertEqual(fr, typing.ForwardRef('int')) 1513 self.assertNotEqual(List['int'], List[int]) 1514 1515 def test_forward_equality_gth(self): 1516 c1 = typing.ForwardRef('C') 1517 c1_gth = typing.ForwardRef('C') 1518 c2 = typing.ForwardRef('C') 1519 c2_gth = typing.ForwardRef('C') 1520 1521 class C: 1522 pass 1523 def foo(a: c1_gth, b: c2_gth): 1524 pass 1525 1526 self.assertEqual(get_type_hints(foo, globals(), locals()), {'a': C, 'b': C}) 1527 self.assertEqual(c1, c2) 1528 self.assertEqual(c1, c1_gth) 1529 self.assertEqual(c1_gth, c2_gth) 1530 self.assertEqual(List[c1], List[c1_gth]) 1531 self.assertNotEqual(List[c1], List[C]) 1532 self.assertNotEqual(List[c1_gth], List[C]) 1533 self.assertEquals(Union[c1, c1_gth], Union[c1]) 1534 self.assertEquals(Union[c1, c1_gth, int], Union[c1, int]) 1535 1536 def test_forward_equality_hash(self): 1537 c1 = typing.ForwardRef('int') 1538 c1_gth = typing.ForwardRef('int') 1539 c2 = typing.ForwardRef('int') 1540 c2_gth = typing.ForwardRef('int') 1541 1542 def foo(a: c1_gth, b: c2_gth): 1543 pass 1544 get_type_hints(foo, globals(), locals()) 1545 1546 self.assertEqual(hash(c1), hash(c2)) 1547 self.assertEqual(hash(c1_gth), hash(c2_gth)) 1548 self.assertEqual(hash(c1), hash(c1_gth)) 1549 1550 def test_forward_equality_namespace(self): 1551 class A: 1552 pass 1553 def namespace1(): 1554 a = typing.ForwardRef('A') 1555 def fun(x: a): 1556 pass 1557 get_type_hints(fun, globals(), locals()) 1558 return a 1559 1560 def namespace2(): 1561 a = typing.ForwardRef('A') 1562 1563 class A: 1564 pass 1565 def fun(x: a): 1566 pass 1567 1568 get_type_hints(fun, globals(), locals()) 1569 return a 1570 1571 self.assertEqual(namespace1(), namespace1()) 1572 self.assertNotEqual(namespace1(), namespace2()) 1573 1574 def test_forward_repr(self): 1575 self.assertEqual(repr(List['int']), "typing.List[ForwardRef('int')]") 1576 1577 def test_union_forward(self): 1578 1579 def foo(a: Union['T']): 1580 pass 1581 1582 self.assertEqual(get_type_hints(foo, globals(), locals()), 1583 {'a': Union[T]}) 1584 1585 def test_tuple_forward(self): 1586 1587 def foo(a: Tuple['T']): 1588 pass 1589 1590 self.assertEqual(get_type_hints(foo, globals(), locals()), 1591 {'a': Tuple[T]}) 1592 1593 def test_forward_recursion_actually(self): 1594 def namespace1(): 1595 a = typing.ForwardRef('A') 1596 A = a 1597 def fun(x: a): pass 1598 1599 ret = get_type_hints(fun, globals(), locals()) 1600 return a 1601 1602 def namespace2(): 1603 a = typing.ForwardRef('A') 1604 A = a 1605 def fun(x: a): pass 1606 1607 ret = get_type_hints(fun, globals(), locals()) 1608 return a 1609 1610 def cmp(o1, o2): 1611 return o1 == o2 1612 1613 r1 = namespace1() 1614 r2 = namespace2() 1615 self.assertIsNot(r1, r2) 1616 self.assertRaises(RecursionError, cmp, r1, r2) 1617 1618 def test_union_forward_recursion(self): 1619 ValueList = List['Value'] 1620 Value = Union[str, ValueList] 1621 1622 class C: 1623 foo: List[Value] 1624 class D: 1625 foo: Union[Value, ValueList] 1626 class E: 1627 foo: Union[List[Value], ValueList] 1628 class F: 1629 foo: Union[Value, List[Value], ValueList] 1630 1631 self.assertEqual(get_type_hints(C, globals(), locals()), get_type_hints(C, globals(), locals())) 1632 self.assertEqual(get_type_hints(C, globals(), locals()), 1633 {'foo': List[Union[str, List[Union[str, List['Value']]]]]}) 1634 self.assertEqual(get_type_hints(D, globals(), locals()), 1635 {'foo': Union[str, List[Union[str, List['Value']]]]}) 1636 self.assertEqual(get_type_hints(E, globals(), locals()), 1637 {'foo': Union[ 1638 List[Union[str, List[Union[str, List['Value']]]]], 1639 List[Union[str, List['Value']]] 1640 ] 1641 }) 1642 self.assertEqual(get_type_hints(F, globals(), locals()), 1643 {'foo': Union[ 1644 str, 1645 List[Union[str, List['Value']]], 1646 List[Union[str, List[Union[str, List['Value']]]]] 1647 ] 1648 }) 1649 1650 def test_callable_forward(self): 1651 1652 def foo(a: Callable[['T'], 'T']): 1653 pass 1654 1655 self.assertEqual(get_type_hints(foo, globals(), locals()), 1656 {'a': Callable[[T], T]}) 1657 1658 def test_callable_with_ellipsis_forward(self): 1659 1660 def foo(a: 'Callable[..., T]'): 1661 pass 1662 1663 self.assertEqual(get_type_hints(foo, globals(), locals()), 1664 {'a': Callable[..., T]}) 1665 1666 def test_syntax_error(self): 1667 1668 with self.assertRaises(SyntaxError): 1669 Generic['/T'] 1670 1671 def test_delayed_syntax_error(self): 1672 1673 def foo(a: 'Node[T'): 1674 pass 1675 1676 with self.assertRaises(SyntaxError): 1677 get_type_hints(foo) 1678 1679 def test_type_error(self): 1680 1681 def foo(a: Tuple['42']): 1682 pass 1683 1684 with self.assertRaises(TypeError): 1685 get_type_hints(foo) 1686 1687 def test_name_error(self): 1688 1689 def foo(a: 'Noode[T]'): 1690 pass 1691 1692 with self.assertRaises(NameError): 1693 get_type_hints(foo, locals()) 1694 1695 def test_no_type_check(self): 1696 1697 @no_type_check 1698 def foo(a: 'whatevers') -> {}: 1699 pass 1700 1701 th = get_type_hints(foo) 1702 self.assertEqual(th, {}) 1703 1704 def test_no_type_check_class(self): 1705 1706 @no_type_check 1707 class C: 1708 def foo(a: 'whatevers') -> {}: 1709 pass 1710 1711 cth = get_type_hints(C.foo) 1712 self.assertEqual(cth, {}) 1713 ith = get_type_hints(C().foo) 1714 self.assertEqual(ith, {}) 1715 1716 def test_no_type_check_no_bases(self): 1717 class C: 1718 def meth(self, x: int): ... 1719 @no_type_check 1720 class D(C): 1721 c = C 1722 # verify that @no_type_check never affects bases 1723 self.assertEqual(get_type_hints(C.meth), {'x': int}) 1724 1725 def test_no_type_check_forward_ref_as_string(self): 1726 class C: 1727 foo: typing.ClassVar[int] = 7 1728 class D: 1729 foo: ClassVar[int] = 7 1730 class E: 1731 foo: 'typing.ClassVar[int]' = 7 1732 class F: 1733 foo: 'ClassVar[int]' = 7 1734 1735 expected_result = {'foo': typing.ClassVar[int]} 1736 for clazz in [C, D, E, F]: 1737 self.assertEqual(get_type_hints(clazz), expected_result) 1738 1739 def test_nested_classvar_fails_forward_ref_check(self): 1740 class E: 1741 foo: 'typing.ClassVar[typing.ClassVar[int]]' = 7 1742 class F: 1743 foo: ClassVar['ClassVar[int]'] = 7 1744 1745 for clazz in [E, F]: 1746 with self.assertRaises(TypeError): 1747 get_type_hints(clazz) 1748 1749 def test_meta_no_type_check(self): 1750 1751 @no_type_check_decorator 1752 def magic_decorator(func): 1753 return func 1754 1755 self.assertEqual(magic_decorator.__name__, 'magic_decorator') 1756 1757 @magic_decorator 1758 def foo(a: 'whatevers') -> {}: 1759 pass 1760 1761 @magic_decorator 1762 class C: 1763 def foo(a: 'whatevers') -> {}: 1764 pass 1765 1766 self.assertEqual(foo.__name__, 'foo') 1767 th = get_type_hints(foo) 1768 self.assertEqual(th, {}) 1769 cth = get_type_hints(C.foo) 1770 self.assertEqual(cth, {}) 1771 ith = get_type_hints(C().foo) 1772 self.assertEqual(ith, {}) 1773 1774 def test_default_globals(self): 1775 code = ("class C:\n" 1776 " def foo(self, a: 'C') -> 'D': pass\n" 1777 "class D:\n" 1778 " def bar(self, b: 'D') -> C: pass\n" 1779 ) 1780 ns = {} 1781 exec(code, ns) 1782 hints = get_type_hints(ns['C'].foo) 1783 self.assertEqual(hints, {'a': ns['C'], 'return': ns['D']}) 1784 1785 1786class OverloadTests(BaseTestCase): 1787 1788 def test_overload_fails(self): 1789 from typing import overload 1790 1791 with self.assertRaises(RuntimeError): 1792 1793 @overload 1794 def blah(): 1795 pass 1796 1797 blah() 1798 1799 def test_overload_succeeds(self): 1800 from typing import overload 1801 1802 @overload 1803 def blah(): 1804 pass 1805 1806 def blah(): 1807 pass 1808 1809 blah() 1810 1811 1812ASYNCIO_TESTS = """ 1813import asyncio 1814 1815T_a = TypeVar('T_a') 1816 1817class AwaitableWrapper(typing.Awaitable[T_a]): 1818 1819 def __init__(self, value): 1820 self.value = value 1821 1822 def __await__(self) -> typing.Iterator[T_a]: 1823 yield 1824 return self.value 1825 1826class AsyncIteratorWrapper(typing.AsyncIterator[T_a]): 1827 1828 def __init__(self, value: typing.Iterable[T_a]): 1829 self.value = value 1830 1831 def __aiter__(self) -> typing.AsyncIterator[T_a]: 1832 return self 1833 1834 @asyncio.coroutine 1835 def __anext__(self) -> T_a: 1836 data = yield from self.value 1837 if data: 1838 return data 1839 else: 1840 raise StopAsyncIteration 1841 1842class ACM: 1843 async def __aenter__(self) -> int: 1844 return 42 1845 async def __aexit__(self, etype, eval, tb): 1846 return None 1847""" 1848 1849try: 1850 exec(ASYNCIO_TESTS) 1851except ImportError: 1852 ASYNCIO = False # multithreading is not enabled 1853else: 1854 ASYNCIO = True 1855 1856# Definitions needed for features introduced in Python 3.6 1857 1858from test import ann_module, ann_module2, ann_module3 1859from typing import AsyncContextManager 1860 1861class A: 1862 y: float 1863class B(A): 1864 x: ClassVar[Optional['B']] = None 1865 y: int 1866 b: int 1867class CSub(B): 1868 z: ClassVar['CSub'] = B() 1869class G(Generic[T]): 1870 lst: ClassVar[List[T]] = [] 1871 1872class NoneAndForward: 1873 parent: 'NoneAndForward' 1874 meaning: None 1875 1876class CoolEmployee(NamedTuple): 1877 name: str 1878 cool: int 1879 1880class CoolEmployeeWithDefault(NamedTuple): 1881 name: str 1882 cool: int = 0 1883 1884class XMeth(NamedTuple): 1885 x: int 1886 def double(self): 1887 return 2 * self.x 1888 1889class XRepr(NamedTuple): 1890 x: int 1891 y: int = 1 1892 def __str__(self): 1893 return f'{self.x} -> {self.y}' 1894 def __add__(self, other): 1895 return 0 1896 1897class HasForeignBaseClass(mod_generics_cache.A): 1898 some_xrepr: 'XRepr' 1899 other_a: 'mod_generics_cache.A' 1900 1901async def g_with(am: AsyncContextManager[int]): 1902 x: int 1903 async with am as x: 1904 return x 1905 1906try: 1907 g_with(ACM()).send(None) 1908except StopIteration as e: 1909 assert e.args[0] == 42 1910 1911gth = get_type_hints 1912 1913class ForRefExample: 1914 @ann_module.dec 1915 def func(self: 'ForRefExample'): 1916 pass 1917 1918 @ann_module.dec 1919 @ann_module.dec 1920 def nested(self: 'ForRefExample'): 1921 pass 1922 1923 1924class GetTypeHintTests(BaseTestCase): 1925 def test_get_type_hints_from_various_objects(self): 1926 # For invalid objects should fail with TypeError (not AttributeError etc). 1927 with self.assertRaises(TypeError): 1928 gth(123) 1929 with self.assertRaises(TypeError): 1930 gth('abc') 1931 with self.assertRaises(TypeError): 1932 gth(None) 1933 1934 def test_get_type_hints_modules(self): 1935 ann_module_type_hints = {1: 2, 'f': Tuple[int, int], 'x': int, 'y': str} 1936 self.assertEqual(gth(ann_module), ann_module_type_hints) 1937 self.assertEqual(gth(ann_module2), {}) 1938 self.assertEqual(gth(ann_module3), {}) 1939 1940 @skip("known bug") 1941 def test_get_type_hints_modules_forwardref(self): 1942 # FIXME: This currently exposes a bug in typing. Cached forward references 1943 # don't account for the case where there are multiple types of the same 1944 # name coming from different modules in the same program. 1945 mgc_hints = {'default_a': Optional[mod_generics_cache.A], 1946 'default_b': Optional[mod_generics_cache.B]} 1947 self.assertEqual(gth(mod_generics_cache), mgc_hints) 1948 1949 def test_get_type_hints_classes(self): 1950 self.assertEqual(gth(ann_module.C), # gth will find the right globalns 1951 {'y': Optional[ann_module.C]}) 1952 self.assertIsInstance(gth(ann_module.j_class), dict) 1953 self.assertEqual(gth(ann_module.M), {'123': 123, 'o': type}) 1954 self.assertEqual(gth(ann_module.D), 1955 {'j': str, 'k': str, 'y': Optional[ann_module.C]}) 1956 self.assertEqual(gth(ann_module.Y), {'z': int}) 1957 self.assertEqual(gth(ann_module.h_class), 1958 {'y': Optional[ann_module.C]}) 1959 self.assertEqual(gth(ann_module.S), {'x': str, 'y': str}) 1960 self.assertEqual(gth(ann_module.foo), {'x': int}) 1961 self.assertEqual(gth(NoneAndForward), 1962 {'parent': NoneAndForward, 'meaning': type(None)}) 1963 self.assertEqual(gth(HasForeignBaseClass), 1964 {'some_xrepr': XRepr, 'other_a': mod_generics_cache.A, 1965 'some_b': mod_generics_cache.B}) 1966 self.assertEqual(gth(XRepr.__new__), 1967 {'x': int, 'y': int}) 1968 self.assertEqual(gth(mod_generics_cache.B), 1969 {'my_inner_a1': mod_generics_cache.B.A, 1970 'my_inner_a2': mod_generics_cache.B.A, 1971 'my_outer_a': mod_generics_cache.A}) 1972 1973 def test_respect_no_type_check(self): 1974 @no_type_check 1975 class NoTpCheck: 1976 class Inn: 1977 def __init__(self, x: 'not a type'): ... 1978 self.assertTrue(NoTpCheck.__no_type_check__) 1979 self.assertTrue(NoTpCheck.Inn.__init__.__no_type_check__) 1980 self.assertEqual(gth(ann_module2.NTC.meth), {}) 1981 class ABase(Generic[T]): 1982 def meth(x: int): ... 1983 @no_type_check 1984 class Der(ABase): ... 1985 self.assertEqual(gth(ABase.meth), {'x': int}) 1986 1987 def test_get_type_hints_for_builtins(self): 1988 # Should not fail for built-in classes and functions. 1989 self.assertEqual(gth(int), {}) 1990 self.assertEqual(gth(type), {}) 1991 self.assertEqual(gth(dir), {}) 1992 self.assertEqual(gth(len), {}) 1993 self.assertEqual(gth(object.__str__), {}) 1994 self.assertEqual(gth(object().__str__), {}) 1995 self.assertEqual(gth(str.join), {}) 1996 1997 def test_previous_behavior(self): 1998 def testf(x, y): ... 1999 testf.__annotations__['x'] = 'int' 2000 self.assertEqual(gth(testf), {'x': int}) 2001 def testg(x: None): ... 2002 self.assertEqual(gth(testg), {'x': type(None)}) 2003 2004 def test_get_type_hints_for_object_with_annotations(self): 2005 class A: ... 2006 class B: ... 2007 b = B() 2008 b.__annotations__ = {'x': 'A'} 2009 self.assertEqual(gth(b, locals()), {'x': A}) 2010 2011 def test_get_type_hints_ClassVar(self): 2012 self.assertEqual(gth(ann_module2.CV, ann_module2.__dict__), 2013 {'var': typing.ClassVar[ann_module2.CV]}) 2014 self.assertEqual(gth(B, globals()), 2015 {'y': int, 'x': ClassVar[Optional[B]], 'b': int}) 2016 self.assertEqual(gth(CSub, globals()), 2017 {'z': ClassVar[CSub], 'y': int, 'b': int, 2018 'x': ClassVar[Optional[B]]}) 2019 self.assertEqual(gth(G), {'lst': ClassVar[List[T]]}) 2020 2021 def test_get_type_hints_wrapped_decoratored_func(self): 2022 expects = {'self': ForRefExample} 2023 self.assertEqual(gth(ForRefExample.func), expects) 2024 self.assertEqual(gth(ForRefExample.nested), expects) 2025 2026 2027class CollectionsAbcTests(BaseTestCase): 2028 2029 def test_hashable(self): 2030 self.assertIsInstance(42, typing.Hashable) 2031 self.assertNotIsInstance([], typing.Hashable) 2032 2033 def test_iterable(self): 2034 self.assertIsInstance([], typing.Iterable) 2035 # Due to ABC caching, the second time takes a separate code 2036 # path and could fail. So call this a few times. 2037 self.assertIsInstance([], typing.Iterable) 2038 self.assertIsInstance([], typing.Iterable) 2039 self.assertNotIsInstance(42, typing.Iterable) 2040 # Just in case, also test issubclass() a few times. 2041 self.assertIsSubclass(list, typing.Iterable) 2042 self.assertIsSubclass(list, typing.Iterable) 2043 2044 def test_iterator(self): 2045 it = iter([]) 2046 self.assertIsInstance(it, typing.Iterator) 2047 self.assertNotIsInstance(42, typing.Iterator) 2048 2049 @skipUnless(ASYNCIO, 'Python 3.5 and multithreading required') 2050 def test_awaitable(self): 2051 ns = {} 2052 exec( 2053 "async def foo() -> typing.Awaitable[int]:\n" 2054 " return await AwaitableWrapper(42)\n", 2055 globals(), ns) 2056 foo = ns['foo'] 2057 g = foo() 2058 self.assertIsInstance(g, typing.Awaitable) 2059 self.assertNotIsInstance(foo, typing.Awaitable) 2060 g.send(None) # Run foo() till completion, to avoid warning. 2061 2062 @skipUnless(ASYNCIO, 'Python 3.5 and multithreading required') 2063 def test_coroutine(self): 2064 ns = {} 2065 exec( 2066 "async def foo():\n" 2067 " return\n", 2068 globals(), ns) 2069 foo = ns['foo'] 2070 g = foo() 2071 self.assertIsInstance(g, typing.Coroutine) 2072 with self.assertRaises(TypeError): 2073 isinstance(g, typing.Coroutine[int]) 2074 self.assertNotIsInstance(foo, typing.Coroutine) 2075 try: 2076 g.send(None) 2077 except StopIteration: 2078 pass 2079 2080 @skipUnless(ASYNCIO, 'Python 3.5 and multithreading required') 2081 def test_async_iterable(self): 2082 base_it = range(10) # type: Iterator[int] 2083 it = AsyncIteratorWrapper(base_it) 2084 self.assertIsInstance(it, typing.AsyncIterable) 2085 self.assertIsInstance(it, typing.AsyncIterable) 2086 self.assertNotIsInstance(42, typing.AsyncIterable) 2087 2088 @skipUnless(ASYNCIO, 'Python 3.5 and multithreading required') 2089 def test_async_iterator(self): 2090 base_it = range(10) # type: Iterator[int] 2091 it = AsyncIteratorWrapper(base_it) 2092 self.assertIsInstance(it, typing.AsyncIterator) 2093 self.assertNotIsInstance(42, typing.AsyncIterator) 2094 2095 def test_sized(self): 2096 self.assertIsInstance([], typing.Sized) 2097 self.assertNotIsInstance(42, typing.Sized) 2098 2099 def test_container(self): 2100 self.assertIsInstance([], typing.Container) 2101 self.assertNotIsInstance(42, typing.Container) 2102 2103 def test_collection(self): 2104 if hasattr(typing, 'Collection'): 2105 self.assertIsInstance(tuple(), typing.Collection) 2106 self.assertIsInstance(frozenset(), typing.Collection) 2107 self.assertIsSubclass(dict, typing.Collection) 2108 self.assertNotIsInstance(42, typing.Collection) 2109 2110 def test_abstractset(self): 2111 self.assertIsInstance(set(), typing.AbstractSet) 2112 self.assertNotIsInstance(42, typing.AbstractSet) 2113 2114 def test_mutableset(self): 2115 self.assertIsInstance(set(), typing.MutableSet) 2116 self.assertNotIsInstance(frozenset(), typing.MutableSet) 2117 2118 def test_mapping(self): 2119 self.assertIsInstance({}, typing.Mapping) 2120 self.assertNotIsInstance(42, typing.Mapping) 2121 2122 def test_mutablemapping(self): 2123 self.assertIsInstance({}, typing.MutableMapping) 2124 self.assertNotIsInstance(42, typing.MutableMapping) 2125 2126 def test_sequence(self): 2127 self.assertIsInstance([], typing.Sequence) 2128 self.assertNotIsInstance(42, typing.Sequence) 2129 2130 def test_mutablesequence(self): 2131 self.assertIsInstance([], typing.MutableSequence) 2132 self.assertNotIsInstance((), typing.MutableSequence) 2133 2134 def test_bytestring(self): 2135 self.assertIsInstance(b'', typing.ByteString) 2136 self.assertIsInstance(bytearray(b''), typing.ByteString) 2137 2138 def test_list(self): 2139 self.assertIsSubclass(list, typing.List) 2140 2141 def test_deque(self): 2142 self.assertIsSubclass(collections.deque, typing.Deque) 2143 class MyDeque(typing.Deque[int]): ... 2144 self.assertIsInstance(MyDeque(), collections.deque) 2145 2146 def test_counter(self): 2147 self.assertIsSubclass(collections.Counter, typing.Counter) 2148 2149 def test_set(self): 2150 self.assertIsSubclass(set, typing.Set) 2151 self.assertNotIsSubclass(frozenset, typing.Set) 2152 2153 def test_frozenset(self): 2154 self.assertIsSubclass(frozenset, typing.FrozenSet) 2155 self.assertNotIsSubclass(set, typing.FrozenSet) 2156 2157 def test_dict(self): 2158 self.assertIsSubclass(dict, typing.Dict) 2159 2160 def test_no_list_instantiation(self): 2161 with self.assertRaises(TypeError): 2162 typing.List() 2163 with self.assertRaises(TypeError): 2164 typing.List[T]() 2165 with self.assertRaises(TypeError): 2166 typing.List[int]() 2167 2168 def test_list_subclass(self): 2169 2170 class MyList(typing.List[int]): 2171 pass 2172 2173 a = MyList() 2174 self.assertIsInstance(a, MyList) 2175 self.assertIsInstance(a, typing.Sequence) 2176 2177 self.assertIsSubclass(MyList, list) 2178 self.assertNotIsSubclass(list, MyList) 2179 2180 def test_no_dict_instantiation(self): 2181 with self.assertRaises(TypeError): 2182 typing.Dict() 2183 with self.assertRaises(TypeError): 2184 typing.Dict[KT, VT]() 2185 with self.assertRaises(TypeError): 2186 typing.Dict[str, int]() 2187 2188 def test_dict_subclass(self): 2189 2190 class MyDict(typing.Dict[str, int]): 2191 pass 2192 2193 d = MyDict() 2194 self.assertIsInstance(d, MyDict) 2195 self.assertIsInstance(d, typing.MutableMapping) 2196 2197 self.assertIsSubclass(MyDict, dict) 2198 self.assertNotIsSubclass(dict, MyDict) 2199 2200 def test_defaultdict_instantiation(self): 2201 self.assertIs(type(typing.DefaultDict()), collections.defaultdict) 2202 self.assertIs(type(typing.DefaultDict[KT, VT]()), collections.defaultdict) 2203 self.assertIs(type(typing.DefaultDict[str, int]()), collections.defaultdict) 2204 2205 def test_defaultdict_subclass(self): 2206 2207 class MyDefDict(typing.DefaultDict[str, int]): 2208 pass 2209 2210 dd = MyDefDict() 2211 self.assertIsInstance(dd, MyDefDict) 2212 2213 self.assertIsSubclass(MyDefDict, collections.defaultdict) 2214 self.assertNotIsSubclass(collections.defaultdict, MyDefDict) 2215 2216 def test_ordereddict_instantiation(self): 2217 self.assertIs(type(typing.OrderedDict()), collections.OrderedDict) 2218 self.assertIs(type(typing.OrderedDict[KT, VT]()), collections.OrderedDict) 2219 self.assertIs(type(typing.OrderedDict[str, int]()), collections.OrderedDict) 2220 2221 def test_ordereddict_subclass(self): 2222 2223 class MyOrdDict(typing.OrderedDict[str, int]): 2224 pass 2225 2226 od = MyOrdDict() 2227 self.assertIsInstance(od, MyOrdDict) 2228 2229 self.assertIsSubclass(MyOrdDict, collections.OrderedDict) 2230 self.assertNotIsSubclass(collections.OrderedDict, MyOrdDict) 2231 2232 @skipUnless(sys.version_info >= (3, 3), 'ChainMap was added in 3.3') 2233 def test_chainmap_instantiation(self): 2234 self.assertIs(type(typing.ChainMap()), collections.ChainMap) 2235 self.assertIs(type(typing.ChainMap[KT, VT]()), collections.ChainMap) 2236 self.assertIs(type(typing.ChainMap[str, int]()), collections.ChainMap) 2237 class CM(typing.ChainMap[KT, VT]): ... 2238 self.assertIs(type(CM[int, str]()), CM) 2239 2240 @skipUnless(sys.version_info >= (3, 3), 'ChainMap was added in 3.3') 2241 def test_chainmap_subclass(self): 2242 2243 class MyChainMap(typing.ChainMap[str, int]): 2244 pass 2245 2246 cm = MyChainMap() 2247 self.assertIsInstance(cm, MyChainMap) 2248 2249 self.assertIsSubclass(MyChainMap, collections.ChainMap) 2250 self.assertNotIsSubclass(collections.ChainMap, MyChainMap) 2251 2252 def test_deque_instantiation(self): 2253 self.assertIs(type(typing.Deque()), collections.deque) 2254 self.assertIs(type(typing.Deque[T]()), collections.deque) 2255 self.assertIs(type(typing.Deque[int]()), collections.deque) 2256 class D(typing.Deque[T]): ... 2257 self.assertIs(type(D[int]()), D) 2258 2259 def test_counter_instantiation(self): 2260 self.assertIs(type(typing.Counter()), collections.Counter) 2261 self.assertIs(type(typing.Counter[T]()), collections.Counter) 2262 self.assertIs(type(typing.Counter[int]()), collections.Counter) 2263 class C(typing.Counter[T]): ... 2264 self.assertIs(type(C[int]()), C) 2265 2266 def test_counter_subclass_instantiation(self): 2267 2268 class MyCounter(typing.Counter[int]): 2269 pass 2270 2271 d = MyCounter() 2272 self.assertIsInstance(d, MyCounter) 2273 self.assertIsInstance(d, typing.Counter) 2274 self.assertIsInstance(d, collections.Counter) 2275 2276 def test_no_set_instantiation(self): 2277 with self.assertRaises(TypeError): 2278 typing.Set() 2279 with self.assertRaises(TypeError): 2280 typing.Set[T]() 2281 with self.assertRaises(TypeError): 2282 typing.Set[int]() 2283 2284 def test_set_subclass_instantiation(self): 2285 2286 class MySet(typing.Set[int]): 2287 pass 2288 2289 d = MySet() 2290 self.assertIsInstance(d, MySet) 2291 2292 def test_no_frozenset_instantiation(self): 2293 with self.assertRaises(TypeError): 2294 typing.FrozenSet() 2295 with self.assertRaises(TypeError): 2296 typing.FrozenSet[T]() 2297 with self.assertRaises(TypeError): 2298 typing.FrozenSet[int]() 2299 2300 def test_frozenset_subclass_instantiation(self): 2301 2302 class MyFrozenSet(typing.FrozenSet[int]): 2303 pass 2304 2305 d = MyFrozenSet() 2306 self.assertIsInstance(d, MyFrozenSet) 2307 2308 def test_no_tuple_instantiation(self): 2309 with self.assertRaises(TypeError): 2310 Tuple() 2311 with self.assertRaises(TypeError): 2312 Tuple[T]() 2313 with self.assertRaises(TypeError): 2314 Tuple[int]() 2315 2316 def test_generator(self): 2317 def foo(): 2318 yield 42 2319 g = foo() 2320 self.assertIsSubclass(type(g), typing.Generator) 2321 2322 def test_no_generator_instantiation(self): 2323 with self.assertRaises(TypeError): 2324 typing.Generator() 2325 with self.assertRaises(TypeError): 2326 typing.Generator[T, T, T]() 2327 with self.assertRaises(TypeError): 2328 typing.Generator[int, int, int]() 2329 2330 def test_async_generator(self): 2331 ns = {} 2332 exec("async def f():\n" 2333 " yield 42\n", globals(), ns) 2334 g = ns['f']() 2335 self.assertIsSubclass(type(g), typing.AsyncGenerator) 2336 2337 def test_no_async_generator_instantiation(self): 2338 with self.assertRaises(TypeError): 2339 typing.AsyncGenerator() 2340 with self.assertRaises(TypeError): 2341 typing.AsyncGenerator[T, T]() 2342 with self.assertRaises(TypeError): 2343 typing.AsyncGenerator[int, int]() 2344 2345 def test_subclassing(self): 2346 2347 class MMA(typing.MutableMapping): 2348 pass 2349 2350 with self.assertRaises(TypeError): # It's abstract 2351 MMA() 2352 2353 class MMC(MMA): 2354 def __getitem__(self, k): 2355 return None 2356 def __setitem__(self, k, v): 2357 pass 2358 def __delitem__(self, k): 2359 pass 2360 def __iter__(self): 2361 return iter(()) 2362 def __len__(self): 2363 return 0 2364 2365 self.assertEqual(len(MMC()), 0) 2366 assert callable(MMC.update) 2367 self.assertIsInstance(MMC(), typing.Mapping) 2368 2369 class MMB(typing.MutableMapping[KT, VT]): 2370 def __getitem__(self, k): 2371 return None 2372 def __setitem__(self, k, v): 2373 pass 2374 def __delitem__(self, k): 2375 pass 2376 def __iter__(self): 2377 return iter(()) 2378 def __len__(self): 2379 return 0 2380 2381 self.assertEqual(len(MMB()), 0) 2382 self.assertEqual(len(MMB[str, str]()), 0) 2383 self.assertEqual(len(MMB[KT, VT]()), 0) 2384 2385 self.assertNotIsSubclass(dict, MMA) 2386 self.assertNotIsSubclass(dict, MMB) 2387 2388 self.assertIsSubclass(MMA, typing.Mapping) 2389 self.assertIsSubclass(MMB, typing.Mapping) 2390 self.assertIsSubclass(MMC, typing.Mapping) 2391 2392 self.assertIsInstance(MMB[KT, VT](), typing.Mapping) 2393 self.assertIsInstance(MMB[KT, VT](), collections.abc.Mapping) 2394 2395 self.assertIsSubclass(MMA, collections.abc.Mapping) 2396 self.assertIsSubclass(MMB, collections.abc.Mapping) 2397 self.assertIsSubclass(MMC, collections.abc.Mapping) 2398 2399 with self.assertRaises(TypeError): 2400 issubclass(MMB[str, str], typing.Mapping) 2401 self.assertIsSubclass(MMC, MMA) 2402 2403 class I(typing.Iterable): ... 2404 self.assertNotIsSubclass(list, I) 2405 2406 class G(typing.Generator[int, int, int]): ... 2407 def g(): yield 0 2408 self.assertIsSubclass(G, typing.Generator) 2409 self.assertIsSubclass(G, typing.Iterable) 2410 self.assertIsSubclass(G, collections.abc.Generator) 2411 self.assertIsSubclass(G, collections.abc.Iterable) 2412 self.assertNotIsSubclass(type(g), G) 2413 2414 def test_subclassing_async_generator(self): 2415 class G(typing.AsyncGenerator[int, int]): 2416 def asend(self, value): 2417 pass 2418 def athrow(self, typ, val=None, tb=None): 2419 pass 2420 2421 ns = {} 2422 exec('async def g(): yield 0', globals(), ns) 2423 g = ns['g'] 2424 self.assertIsSubclass(G, typing.AsyncGenerator) 2425 self.assertIsSubclass(G, typing.AsyncIterable) 2426 self.assertIsSubclass(G, collections.abc.AsyncGenerator) 2427 self.assertIsSubclass(G, collections.abc.AsyncIterable) 2428 self.assertNotIsSubclass(type(g), G) 2429 2430 instance = G() 2431 self.assertIsInstance(instance, typing.AsyncGenerator) 2432 self.assertIsInstance(instance, typing.AsyncIterable) 2433 self.assertIsInstance(instance, collections.abc.AsyncGenerator) 2434 self.assertIsInstance(instance, collections.abc.AsyncIterable) 2435 self.assertNotIsInstance(type(g), G) 2436 self.assertNotIsInstance(g, G) 2437 2438 def test_subclassing_subclasshook(self): 2439 2440 class Base(typing.Iterable): 2441 @classmethod 2442 def __subclasshook__(cls, other): 2443 if other.__name__ == 'Foo': 2444 return True 2445 else: 2446 return False 2447 2448 class C(Base): ... 2449 class Foo: ... 2450 class Bar: ... 2451 self.assertIsSubclass(Foo, Base) 2452 self.assertIsSubclass(Foo, C) 2453 self.assertNotIsSubclass(Bar, C) 2454 2455 def test_subclassing_register(self): 2456 2457 class A(typing.Container): ... 2458 class B(A): ... 2459 2460 class C: ... 2461 A.register(C) 2462 self.assertIsSubclass(C, A) 2463 self.assertNotIsSubclass(C, B) 2464 2465 class D: ... 2466 B.register(D) 2467 self.assertIsSubclass(D, A) 2468 self.assertIsSubclass(D, B) 2469 2470 class M(): ... 2471 collections.abc.MutableMapping.register(M) 2472 self.assertIsSubclass(M, typing.Mapping) 2473 2474 def test_collections_as_base(self): 2475 2476 class M(collections.abc.Mapping): ... 2477 self.assertIsSubclass(M, typing.Mapping) 2478 self.assertIsSubclass(M, typing.Iterable) 2479 2480 class S(collections.abc.MutableSequence): ... 2481 self.assertIsSubclass(S, typing.MutableSequence) 2482 self.assertIsSubclass(S, typing.Iterable) 2483 2484 class I(collections.abc.Iterable): ... 2485 self.assertIsSubclass(I, typing.Iterable) 2486 2487 class A(collections.abc.Mapping, metaclass=abc.ABCMeta): ... 2488 class B: ... 2489 A.register(B) 2490 self.assertIsSubclass(B, typing.Mapping) 2491 2492 2493class OtherABCTests(BaseTestCase): 2494 2495 def test_contextmanager(self): 2496 @contextlib.contextmanager 2497 def manager(): 2498 yield 42 2499 2500 cm = manager() 2501 self.assertIsInstance(cm, typing.ContextManager) 2502 self.assertNotIsInstance(42, typing.ContextManager) 2503 2504 @skipUnless(ASYNCIO, 'Python 3.5 required') 2505 def test_async_contextmanager(self): 2506 class NotACM: 2507 pass 2508 self.assertIsInstance(ACM(), typing.AsyncContextManager) 2509 self.assertNotIsInstance(NotACM(), typing.AsyncContextManager) 2510 @contextlib.contextmanager 2511 def manager(): 2512 yield 42 2513 2514 cm = manager() 2515 self.assertNotIsInstance(cm, typing.AsyncContextManager) 2516 self.assertEqual(typing.AsyncContextManager[int].__args__, (int,)) 2517 with self.assertRaises(TypeError): 2518 isinstance(42, typing.AsyncContextManager[int]) 2519 with self.assertRaises(TypeError): 2520 typing.AsyncContextManager[int, str] 2521 2522 2523class TypeTests(BaseTestCase): 2524 2525 def test_type_basic(self): 2526 2527 class User: pass 2528 class BasicUser(User): pass 2529 class ProUser(User): pass 2530 2531 def new_user(user_class: Type[User]) -> User: 2532 return user_class() 2533 2534 new_user(BasicUser) 2535 2536 def test_type_typevar(self): 2537 2538 class User: pass 2539 class BasicUser(User): pass 2540 class ProUser(User): pass 2541 2542 U = TypeVar('U', bound=User) 2543 2544 def new_user(user_class: Type[U]) -> U: 2545 return user_class() 2546 2547 new_user(BasicUser) 2548 2549 def test_type_optional(self): 2550 A = Optional[Type[BaseException]] 2551 2552 def foo(a: A) -> Optional[BaseException]: 2553 if a is None: 2554 return None 2555 else: 2556 return a() 2557 2558 assert isinstance(foo(KeyboardInterrupt), KeyboardInterrupt) 2559 assert foo(None) is None 2560 2561 2562class NewTypeTests(BaseTestCase): 2563 2564 def test_basic(self): 2565 UserId = NewType('UserId', int) 2566 UserName = NewType('UserName', str) 2567 self.assertIsInstance(UserId(5), int) 2568 self.assertIsInstance(UserName('Joe'), str) 2569 self.assertEqual(UserId(5) + 1, 6) 2570 2571 def test_errors(self): 2572 UserId = NewType('UserId', int) 2573 UserName = NewType('UserName', str) 2574 with self.assertRaises(TypeError): 2575 issubclass(UserId, int) 2576 with self.assertRaises(TypeError): 2577 class D(UserName): 2578 pass 2579 2580 2581class NamedTupleTests(BaseTestCase): 2582 class NestedEmployee(NamedTuple): 2583 name: str 2584 cool: int 2585 2586 def test_basics(self): 2587 Emp = NamedTuple('Emp', [('name', str), ('id', int)]) 2588 self.assertIsSubclass(Emp, tuple) 2589 joe = Emp('Joe', 42) 2590 jim = Emp(name='Jim', id=1) 2591 self.assertIsInstance(joe, Emp) 2592 self.assertIsInstance(joe, tuple) 2593 self.assertEqual(joe.name, 'Joe') 2594 self.assertEqual(joe.id, 42) 2595 self.assertEqual(jim.name, 'Jim') 2596 self.assertEqual(jim.id, 1) 2597 self.assertEqual(Emp.__name__, 'Emp') 2598 self.assertEqual(Emp._fields, ('name', 'id')) 2599 self.assertEqual(Emp.__annotations__, 2600 collections.OrderedDict([('name', str), ('id', int)])) 2601 self.assertIs(Emp._field_types, Emp.__annotations__) 2602 2603 def test_namedtuple_pyversion(self): 2604 if sys.version_info[:2] < (3, 6): 2605 with self.assertRaises(TypeError): 2606 NamedTuple('Name', one=int, other=str) 2607 with self.assertRaises(TypeError): 2608 class NotYet(NamedTuple): 2609 whatever = 0 2610 2611 def test_annotation_usage(self): 2612 tim = CoolEmployee('Tim', 9000) 2613 self.assertIsInstance(tim, CoolEmployee) 2614 self.assertIsInstance(tim, tuple) 2615 self.assertEqual(tim.name, 'Tim') 2616 self.assertEqual(tim.cool, 9000) 2617 self.assertEqual(CoolEmployee.__name__, 'CoolEmployee') 2618 self.assertEqual(CoolEmployee._fields, ('name', 'cool')) 2619 self.assertEqual(CoolEmployee.__annotations__, 2620 collections.OrderedDict(name=str, cool=int)) 2621 self.assertIs(CoolEmployee._field_types, CoolEmployee.__annotations__) 2622 2623 def test_annotation_usage_with_default(self): 2624 jelle = CoolEmployeeWithDefault('Jelle') 2625 self.assertIsInstance(jelle, CoolEmployeeWithDefault) 2626 self.assertIsInstance(jelle, tuple) 2627 self.assertEqual(jelle.name, 'Jelle') 2628 self.assertEqual(jelle.cool, 0) 2629 cooler_employee = CoolEmployeeWithDefault('Sjoerd', 1) 2630 self.assertEqual(cooler_employee.cool, 1) 2631 2632 self.assertEqual(CoolEmployeeWithDefault.__name__, 'CoolEmployeeWithDefault') 2633 self.assertEqual(CoolEmployeeWithDefault._fields, ('name', 'cool')) 2634 self.assertEqual(CoolEmployeeWithDefault._field_types, dict(name=str, cool=int)) 2635 self.assertEqual(CoolEmployeeWithDefault._field_defaults, dict(cool=0)) 2636 2637 with self.assertRaises(TypeError): 2638 exec(""" 2639class NonDefaultAfterDefault(NamedTuple): 2640 x: int = 3 2641 y: int 2642""") 2643 2644 def test_annotation_usage_with_methods(self): 2645 self.assertEqual(XMeth(1).double(), 2) 2646 self.assertEqual(XMeth(42).x, XMeth(42)[0]) 2647 self.assertEqual(str(XRepr(42)), '42 -> 1') 2648 self.assertEqual(XRepr(1, 2) + XRepr(3), 0) 2649 2650 with self.assertRaises(AttributeError): 2651 exec(""" 2652class XMethBad(NamedTuple): 2653 x: int 2654 def _fields(self): 2655 return 'no chance for this' 2656""") 2657 2658 with self.assertRaises(AttributeError): 2659 exec(""" 2660class XMethBad2(NamedTuple): 2661 x: int 2662 def _source(self): 2663 return 'no chance for this as well' 2664""") 2665 2666 def test_namedtuple_keyword_usage(self): 2667 LocalEmployee = NamedTuple("LocalEmployee", name=str, age=int) 2668 nick = LocalEmployee('Nick', 25) 2669 self.assertIsInstance(nick, tuple) 2670 self.assertEqual(nick.name, 'Nick') 2671 self.assertEqual(LocalEmployee.__name__, 'LocalEmployee') 2672 self.assertEqual(LocalEmployee._fields, ('name', 'age')) 2673 self.assertEqual(LocalEmployee.__annotations__, dict(name=str, age=int)) 2674 self.assertIs(LocalEmployee._field_types, LocalEmployee.__annotations__) 2675 with self.assertRaises(TypeError): 2676 NamedTuple('Name', [('x', int)], y=str) 2677 with self.assertRaises(TypeError): 2678 NamedTuple('Name', x=1, y='a') 2679 2680 def test_namedtuple_special_keyword_names(self): 2681 NT = NamedTuple("NT", cls=type, self=object, typename=str, fields=list) 2682 self.assertEqual(NT.__name__, 'NT') 2683 self.assertEqual(NT._fields, ('cls', 'self', 'typename', 'fields')) 2684 a = NT(cls=str, self=42, typename='foo', fields=[('bar', tuple)]) 2685 self.assertEqual(a.cls, str) 2686 self.assertEqual(a.self, 42) 2687 self.assertEqual(a.typename, 'foo') 2688 self.assertEqual(a.fields, [('bar', tuple)]) 2689 2690 def test_namedtuple_errors(self): 2691 with self.assertRaises(TypeError): 2692 NamedTuple.__new__() 2693 with self.assertRaises(TypeError): 2694 NamedTuple() 2695 with self.assertRaises(TypeError): 2696 NamedTuple('Emp', [('name', str)], None) 2697 with self.assertRaises(ValueError): 2698 NamedTuple('Emp', [('_name', str)]) 2699 2700 Emp = NamedTuple(typename='Emp', name=str, id=int) 2701 self.assertEqual(Emp.__name__, 'Emp') 2702 self.assertEqual(Emp._fields, ('name', 'id')) 2703 2704 Emp = NamedTuple('Emp', fields=[('name', str), ('id', int)]) 2705 self.assertEqual(Emp.__name__, 'Emp') 2706 self.assertEqual(Emp._fields, ('name', 'id')) 2707 2708 def test_copy_and_pickle(self): 2709 global Emp # pickle wants to reference the class by name 2710 Emp = NamedTuple('Emp', [('name', str), ('cool', int)]) 2711 for cls in Emp, CoolEmployee, self.NestedEmployee: 2712 with self.subTest(cls=cls): 2713 jane = cls('jane', 37) 2714 for proto in range(pickle.HIGHEST_PROTOCOL + 1): 2715 z = pickle.dumps(jane, proto) 2716 jane2 = pickle.loads(z) 2717 self.assertEqual(jane2, jane) 2718 self.assertIsInstance(jane2, cls) 2719 2720 jane2 = copy(jane) 2721 self.assertEqual(jane2, jane) 2722 self.assertIsInstance(jane2, cls) 2723 2724 jane2 = deepcopy(jane) 2725 self.assertEqual(jane2, jane) 2726 self.assertIsInstance(jane2, cls) 2727 2728 2729class IOTests(BaseTestCase): 2730 2731 def test_io(self): 2732 2733 def stuff(a: IO) -> AnyStr: 2734 return a.readline() 2735 2736 a = stuff.__annotations__['a'] 2737 self.assertEqual(a.__parameters__, (AnyStr,)) 2738 2739 def test_textio(self): 2740 2741 def stuff(a: TextIO) -> str: 2742 return a.readline() 2743 2744 a = stuff.__annotations__['a'] 2745 self.assertEqual(a.__parameters__, ()) 2746 2747 def test_binaryio(self): 2748 2749 def stuff(a: BinaryIO) -> bytes: 2750 return a.readline() 2751 2752 a = stuff.__annotations__['a'] 2753 self.assertEqual(a.__parameters__, ()) 2754 2755 def test_io_submodule(self): 2756 from typing.io import IO, TextIO, BinaryIO, __all__, __name__ 2757 self.assertIs(IO, typing.IO) 2758 self.assertIs(TextIO, typing.TextIO) 2759 self.assertIs(BinaryIO, typing.BinaryIO) 2760 self.assertEqual(set(__all__), set(['IO', 'TextIO', 'BinaryIO'])) 2761 self.assertEqual(__name__, 'typing.io') 2762 2763 2764class RETests(BaseTestCase): 2765 # Much of this is really testing _TypeAlias. 2766 2767 def test_basics(self): 2768 pat = re.compile('[a-z]+', re.I) 2769 self.assertIsSubclass(pat.__class__, Pattern) 2770 self.assertIsSubclass(type(pat), Pattern) 2771 self.assertIsInstance(pat, Pattern) 2772 2773 mat = pat.search('12345abcde.....') 2774 self.assertIsSubclass(mat.__class__, Match) 2775 self.assertIsSubclass(type(mat), Match) 2776 self.assertIsInstance(mat, Match) 2777 2778 # these should just work 2779 Pattern[Union[str, bytes]] 2780 Match[Union[bytes, str]] 2781 2782 def test_alias_equality(self): 2783 self.assertEqual(Pattern[str], Pattern[str]) 2784 self.assertNotEqual(Pattern[str], Pattern[bytes]) 2785 self.assertNotEqual(Pattern[str], Match[str]) 2786 self.assertNotEqual(Pattern[str], str) 2787 2788 def test_errors(self): 2789 m = Match[Union[str, bytes]] 2790 with self.assertRaises(TypeError): 2791 m[str] 2792 with self.assertRaises(TypeError): 2793 # We don't support isinstance(). 2794 isinstance(42, Pattern[str]) 2795 with self.assertRaises(TypeError): 2796 # We don't support issubclass(). 2797 issubclass(Pattern[bytes], Pattern[str]) 2798 2799 def test_repr(self): 2800 self.assertEqual(repr(Pattern), 'typing.Pattern') 2801 self.assertEqual(repr(Pattern[str]), 'typing.Pattern[str]') 2802 self.assertEqual(repr(Pattern[bytes]), 'typing.Pattern[bytes]') 2803 self.assertEqual(repr(Match), 'typing.Match') 2804 self.assertEqual(repr(Match[str]), 'typing.Match[str]') 2805 self.assertEqual(repr(Match[bytes]), 'typing.Match[bytes]') 2806 2807 def test_re_submodule(self): 2808 from typing.re import Match, Pattern, __all__, __name__ 2809 self.assertIs(Match, typing.Match) 2810 self.assertIs(Pattern, typing.Pattern) 2811 self.assertEqual(set(__all__), set(['Match', 'Pattern'])) 2812 self.assertEqual(__name__, 'typing.re') 2813 2814 def test_cannot_subclass(self): 2815 with self.assertRaises(TypeError) as ex: 2816 2817 class A(typing.Match): 2818 pass 2819 2820 self.assertEqual(str(ex.exception), 2821 "type 're.Match' is not an acceptable base type") 2822 2823 2824class AllTests(BaseTestCase): 2825 """Tests for __all__.""" 2826 2827 def test_all(self): 2828 from typing import __all__ as a 2829 # Just spot-check the first and last of every category. 2830 self.assertIn('AbstractSet', a) 2831 self.assertIn('ValuesView', a) 2832 self.assertIn('cast', a) 2833 self.assertIn('overload', a) 2834 if hasattr(contextlib, 'AbstractContextManager'): 2835 self.assertIn('ContextManager', a) 2836 # Check that io and re are not exported. 2837 self.assertNotIn('io', a) 2838 self.assertNotIn('re', a) 2839 # Spot-check that stdlib modules aren't exported. 2840 self.assertNotIn('os', a) 2841 self.assertNotIn('sys', a) 2842 # Check that Text is defined. 2843 self.assertIn('Text', a) 2844 # Check previously missing classes. 2845 self.assertIn('SupportsBytes', a) 2846 self.assertIn('SupportsComplex', a) 2847 2848 def test_all_exported_names(self): 2849 import typing 2850 2851 actual_all = set(typing.__all__) 2852 computed_all = { 2853 k for k, v in vars(typing).items() 2854 # explicitly exported, not a thing with __module__ 2855 if k in actual_all or ( 2856 # avoid private names 2857 not k.startswith('_') and 2858 # avoid things in the io / re typing submodules 2859 k not in typing.io.__all__ and 2860 k not in typing.re.__all__ and 2861 k not in {'io', 're'} and 2862 # there's a few types and metaclasses that aren't exported 2863 not k.endswith(('Meta', '_contra', '_co')) and 2864 not k.upper() == k and 2865 # but export all things that have __module__ == 'typing' 2866 getattr(v, '__module__', None) == typing.__name__ 2867 ) 2868 } 2869 self.assertSetEqual(computed_all, actual_all) 2870 2871 2872 2873if __name__ == '__main__': 2874 main() 2875