Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

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

Provide feedback

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

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit80e5e8b

Browse files
aliwotriumph1hauntsaninja
authored
Allow to use Final and ClassVar after Python 3.13 (#18358)
This PR allows to use Final and ClassVar after python 3.13I saw this [PR](#10478)and I saw recent changes of python 3.13https://docs.python.org/3/library/typing.html#typing.FinalFinal now can be nested with ClassVar. so I added a version check!---------Co-authored-by: triumph1 <seungwon.jeong@wesang.com>Co-authored-by: hauntsaninja <hauntsaninja@gmail.com>
1 parent9e40be6 commit80e5e8b

File tree

3 files changed

+32
-7
lines changed

3 files changed

+32
-7
lines changed

‎mypy/semanal.py‎

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3658,7 +3658,11 @@ def unwrap_final(self, s: AssignmentStmt) -> bool:
36583658
else:
36593659
s.type=s.unanalyzed_type.args[0]
36603660

3661-
ifs.typeisnotNoneandself.is_classvar(s.type):
3661+
if (
3662+
s.typeisnotNone
3663+
andself.options.python_version< (3,13)
3664+
andself.is_classvar(s.type)
3665+
):
36623666
self.fail("Variable should not be annotated with both ClassVar and Final",s)
36633667
returnFalse
36643668

@@ -7358,6 +7362,7 @@ def type_analyzer(
73587362
allow_unbound_tvars:bool=False,
73597363
allow_placeholder:bool=False,
73607364
allow_typed_dict_special_forms:bool=False,
7365+
allow_final:bool=False,
73617366
allow_param_spec_literals:bool=False,
73627367
allow_unpack:bool=False,
73637368
report_invalid_types:bool=True,
@@ -7379,6 +7384,7 @@ def type_analyzer(
73797384
report_invalid_types=report_invalid_types,
73807385
allow_placeholder=allow_placeholder,
73817386
allow_typed_dict_special_forms=allow_typed_dict_special_forms,
7387+
allow_final=allow_final,
73827388
allow_param_spec_literals=allow_param_spec_literals,
73837389
allow_unpack=allow_unpack,
73847390
prohibit_self_type=prohibit_self_type,
@@ -7403,6 +7409,7 @@ def anal_type(
74037409
allow_unbound_tvars:bool=False,
74047410
allow_placeholder:bool=False,
74057411
allow_typed_dict_special_forms:bool=False,
7412+
allow_final:bool=False,
74067413
allow_param_spec_literals:bool=False,
74077414
allow_unpack:bool=False,
74087415
report_invalid_types:bool=True,
@@ -7439,6 +7446,7 @@ def anal_type(
74397446
allow_tuple_literal=allow_tuple_literal,
74407447
allow_placeholder=allow_placeholder,
74417448
allow_typed_dict_special_forms=allow_typed_dict_special_forms,
7449+
allow_final=allow_final,
74427450
allow_param_spec_literals=allow_param_spec_literals,
74437451
allow_unpack=allow_unpack,
74447452
report_invalid_types=report_invalid_types,

‎mypy/typeanal.py‎

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,7 @@ def __init__(
226226
allow_unbound_tvars:bool=False,
227227
allow_placeholder:bool=False,
228228
allow_typed_dict_special_forms:bool=False,
229+
allow_final:bool=True,
229230
allow_param_spec_literals:bool=False,
230231
allow_unpack:bool=False,
231232
report_invalid_types:bool=True,
@@ -261,6 +262,8 @@ def __init__(
261262
self.allow_placeholder=allow_placeholder
262263
# Are we in a context where Required[] is allowed?
263264
self.allow_typed_dict_special_forms=allow_typed_dict_special_forms
265+
# Set True when we analyze ClassVar else False
266+
self.allow_final=allow_final
264267
# Are we in a context where ParamSpec literals are allowed?
265268
self.allow_param_spec_literals=allow_param_spec_literals
266269
# Are we in context where literal "..." specifically is allowed?
@@ -607,11 +610,12 @@ def try_analyze_special_unbound_type(self, t: UnboundType, fullname: str) -> Typ
607610
code=codes.VALID_TYPE,
608611
)
609612
else:
610-
self.fail(
611-
"Final can be only used as an outermost qualifier in a variable annotation",
612-
t,
613-
code=codes.VALID_TYPE,
614-
)
613+
ifnotself.allow_final:
614+
self.fail(
615+
"Final can be only used as an outermost qualifier in a variable annotation",
616+
t,
617+
code=codes.VALID_TYPE,
618+
)
615619
returnAnyType(TypeOfAny.from_error)
616620
eliffullname=="typing.Tuple"or (
617621
fullname=="builtins.tuple"
@@ -692,7 +696,7 @@ def try_analyze_special_unbound_type(self, t: UnboundType, fullname: str) -> Typ
692696
"ClassVar[...] must have at most one type argument",t,code=codes.VALID_TYPE
693697
)
694698
returnAnyType(TypeOfAny.from_error)
695-
returnself.anal_type(t.args[0])
699+
returnself.anal_type(t.args[0],allow_final=self.options.python_version>= (3,13))
696700
eliffullnameinNEVER_NAMES:
697701
returnUninhabitedType()
698702
eliffullnameinLITERAL_TYPE_NAMES:
@@ -1878,11 +1882,13 @@ def anal_type(
18781882
allow_unpack:bool=False,
18791883
allow_ellipsis:bool=False,
18801884
allow_typed_dict_special_forms:bool=False,
1885+
allow_final:bool=False,
18811886
)->Type:
18821887
ifnested:
18831888
self.nesting_level+=1
18841889
old_allow_typed_dict_special_forms=self.allow_typed_dict_special_forms
18851890
self.allow_typed_dict_special_forms=allow_typed_dict_special_forms
1891+
self.allow_final=allow_final
18861892
old_allow_ellipsis=self.allow_ellipsis
18871893
self.allow_ellipsis=allow_ellipsis
18881894
old_allow_unpack=self.allow_unpack

‎test-data/unit/check-final.test‎

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,7 @@ def g(x: int) -> Final[int]: ... # E: Final can be only used as an outermost qu
194194
[out]
195195

196196
[case testFinalDefiningNotInMethodExtensions]
197+
# flags: --python-version 3.14
197198
from typing_extensions import Final
198199

199200
def f(x: Final[int]) -> int: ... # E: Final can be only used as an outermost qualifier in a variable annotation
@@ -1128,6 +1129,7 @@ class A:
11281129
[builtins fixtures/tuple.pyi]
11291130

11301131
[case testFinalUsedWithClassVar]
1132+
# flags: --python-version 3.12
11311133
from typing import Final, ClassVar
11321134

11331135
class A:
@@ -1136,6 +1138,15 @@ class A:
11361138
c: ClassVar[Final] = 1 # E: Final can be only used as an outermost qualifier in a variable annotation
11371139
[out]
11381140

1141+
[case testFinalUsedWithClassVarAfterPy313]
1142+
# flags: --python-version 3.13
1143+
from typing import Final, ClassVar
1144+
1145+
class A:
1146+
a: Final[ClassVar[int]] = 1
1147+
b: ClassVar[Final[int]] = 1
1148+
c: ClassVar[Final] = 1
1149+
11391150
[case testFinalClassWithAbstractMethod]
11401151
from typing import final
11411152
from abc import ABC, abstractmethod

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp