33"""
44
55from dataclasses import dataclass
6- from typing import Hashable
6+ from typing import Hashable , assert_type
77
88
99@dataclass
1010class DC1 :
1111 a : int
1212
1313
14- # This should generate an error because DC1 isn't hashable.
14+ assert_type (DC1 .__hash__ , None )
15+
16+ # These should generate errors because DC1 isn't hashable.
17+ DC1 (0 ).__hash__ () # E
18+ hash (DC1 (0 )) # E
1519v1 : Hashable = DC1 (0 ) # E
1620
1721
@@ -20,15 +24,26 @@ class DC2:
2024 a : int
2125
2226
23- v2 : Hashable = DC2 (0 )
27+ # Because `DC2` is frozen, type checkers should synthesize
28+ # a callable `__hash__` method for it, and therefore should
29+ # emit a diagnostic here:
30+ assert_type (DC2 .__hash__ , None ) # E
31+
32+ DC2 (0 ).__hash__ () # OK
33+ hash (DC2 (0 )) # OK
34+ v2 : Hashable = DC2 (0 ) # OK
2435
2536
2637@dataclass (eq = True )
2738class DC3 :
2839 a : int
2940
3041
31- # This should generate an error because DC3 isn't hashable.
42+ assert_type (DC3 .__hash__ , None )
43+
44+ # These should generate errors because DC3 isn't hashable.
45+ DC3 (0 ).__hash__ () # E
46+ hash (DC3 (0 )) # E
3247v3 : Hashable = DC3 (0 ) # E
3348
3449
@@ -37,15 +52,29 @@ class DC4:
3752 a : int
3853
3954
40- v4 : Hashable = DC4 (0 )
55+ # Because `DC4` is frozen, type checkers should synthesize
56+ # a callable `__hash__` method for it, and therefore should
57+ # emit a diagnostic here:
58+ assert_type (DC4 .__hash__ , None ) # E
59+
60+ DC4 (0 ).__hash__ () # OK
61+ hash (DC4 (0 )) # OK
62+ v4 : Hashable = DC4 (0 ) # OK
4163
4264
4365@dataclass (eq = True , unsafe_hash = True )
4466class DC5 :
4567 a : int
4668
4769
48- v5 : Hashable = DC5 (0 )
70+ # Type checkers should synthesize a callable `__hash__`
71+ # method for `DC5` due to `unsafe_hash=True`, and therefore
72+ # should emit a diagnostic here:
73+ assert_type (DC5 .__hash__ , None ) # E
74+
75+ DC5 (0 ).__hash__ () # OK
76+ hash (DC5 (0 )) # OK
77+ v5 : Hashable = DC5 (0 ) # OK
4978
5079
5180@dataclass (eq = True )
@@ -56,7 +85,13 @@ def __hash__(self) -> int:
5685 return 0
5786
5887
59- v6 : Hashable = DC6 (0 )
88+ # Type checkers should respect the manually defined `__hash__`
89+ # method for `DC6`, and therefore should emit a diagnostic here:
90+ assert_type (DC6 .__hash__ , None ) # E
91+
92+ DC6 (0 ).__hash__ () # OK
93+ hash (DC6 (0 )) # OK
94+ v6 : Hashable = DC6 (0 ) # OK
6095
6196
6297@dataclass (frozen = True )
@@ -67,4 +102,11 @@ def __eq__(self, other) -> bool:
67102 return self .a == other .a
68103
69104
70- v7 : Hashable = DC7 (0 )
105+ # Because `DC7` is frozen, type checkers should synthesize
106+ # a callable `__hash__` method for it, and therefore should
107+ # emit a diagnostic here:
108+ assert_type (DC7 .__hash__ , None ) # E
109+
110+ DC7 (0 ).__hash__ () # OK
111+ hash (DC7 (0 )) # OK
112+ v7 : Hashable = DC7 (0 ) # OK
0 commit comments