diff --git a/conformance/results/mypy/qualifiers_final_decorator.toml b/conformance/results/mypy/qualifiers_final_decorator.toml index e25fa2c8..514606bb 100644 --- a/conformance/results/mypy/qualifiers_final_decorator.toml +++ b/conformance/results/mypy/qualifiers_final_decorator.toml @@ -1,20 +1,21 @@ conformant = "Pass" output = """ qualifiers_final_decorator.py:21: error: Cannot inherit from final class "Base1" [misc] -qualifiers_final_decorator.py:56: error: Cannot override final attribute "method1" (previously declared in base class "Base2") [misc] -qualifiers_final_decorator.py:59: error: Cannot override final attribute "method2" (previously declared in base class "Base2") [misc] -qualifiers_final_decorator.py:63: error: Cannot override final attribute "method3" (previously declared in base class "Base2") [misc] -qualifiers_final_decorator.py:67: error: Cannot override final attribute "method4" (previously declared in base class "Base2") [misc] -qualifiers_final_decorator.py:80: error: Cannot override final attribute "method" (previously declared in base class "Base3") [misc] -qualifiers_final_decorator.py:84: error: @final should be applied only to overload implementation [misc] -qualifiers_final_decorator.py:94: error: Cannot override final attribute "method" (previously declared in base class "Base4") [misc] -qualifiers_final_decorator.py:118: error: Cannot override final attribute "method" (previously declared in base class "Base5_2") [misc] -qualifiers_final_decorator.py:118: error: Signature of "method" incompatible with supertype "Base5_2" [override] -qualifiers_final_decorator.py:118: note: Superclass: -qualifiers_final_decorator.py:118: note: def method(self, v: int) -> None -qualifiers_final_decorator.py:118: note: Subclass: -qualifiers_final_decorator.py:118: note: def method(self) -> None -qualifiers_final_decorator.py:125: error: @final cannot be used with non-method functions [misc] +qualifiers_final_decorator.py:64: error: Cannot override final attribute "method1" (previously declared in base class "Base2") [misc] +qualifiers_final_decorator.py:67: error: Cannot override final attribute "method2" (previously declared in base class "Base2") [misc] +qualifiers_final_decorator.py:71: error: Cannot override final attribute "method3" (previously declared in base class "Base2") [misc] +qualifiers_final_decorator.py:75: error: Cannot override final attribute "method4" (previously declared in base class "Base2") [misc] +qualifiers_final_decorator.py:86: error: Cannot override final attribute "method5" (previously declared in base class "Base2") [misc] +qualifiers_final_decorator.py:92: error: Cannot override final attribute "method" (previously declared in base class "Base3") [misc] +qualifiers_final_decorator.py:96: error: @final should be applied only to overload implementation [misc] +qualifiers_final_decorator.py:106: error: Cannot override final attribute "method" (previously declared in base class "Base4") [misc] +qualifiers_final_decorator.py:130: error: Cannot override final attribute "method" (previously declared in base class "Base5_2") [misc] +qualifiers_final_decorator.py:130: error: Signature of "method" incompatible with supertype "Base5_2" [override] +qualifiers_final_decorator.py:130: note: Superclass: +qualifiers_final_decorator.py:130: note: def method(self, v: int) -> None +qualifiers_final_decorator.py:130: note: Subclass: +qualifiers_final_decorator.py:130: note: def method(self) -> None +qualifiers_final_decorator.py:137: error: @final cannot be used with non-method functions [misc] """ conformance_automated = "Pass" errors_diff = """ diff --git a/conformance/results/mypy/version.toml b/conformance/results/mypy/version.toml index 3d498066..97e385c3 100644 --- a/conformance/results/mypy/version.toml +++ b/conformance/results/mypy/version.toml @@ -1,2 +1,2 @@ -version = "mypy 1.14.0" -test_duration = 1.6 +version = "mypy 1.14.1" +test_duration = 3.3 diff --git a/conformance/results/pyre/qualifiers_final_decorator.toml b/conformance/results/pyre/qualifiers_final_decorator.toml index ef5be734..137d2a2b 100644 --- a/conformance/results/pyre/qualifiers_final_decorator.toml +++ b/conformance/results/pyre/qualifiers_final_decorator.toml @@ -7,18 +7,19 @@ Reports misleading error when overload is marked @final but implementation is no output = """ qualifiers_final_decorator.py:21:0 Invalid inheritance [39]: Cannot inherit from final class `Base1`. qualifiers_final_decorator.py:51:4 Incompatible overload [43]: This definition does not have the same decorators as the preceding overload(s). -qualifiers_final_decorator.py:56:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method1` cannot override final method defined in `Base2`. -qualifiers_final_decorator.py:60:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method2` cannot override final method defined in `Base2`. -qualifiers_final_decorator.py:64:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method3` cannot override final method defined in `Base2`. -qualifiers_final_decorator.py:75:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method4` cannot override final method defined in `Base2`. -qualifiers_final_decorator.py:86:4 Incompatible overload [43]: This definition does not have the same decorators as the preceding overload(s). -qualifiers_final_decorator.py:118:4 Inconsistent override [14]: `qualifiers_final_decorator.Derived5.method` overrides method defined in `Base5_2` inconsistently. Could not find parameter `v` in overriding signature. -qualifiers_final_decorator.py:118:4 Invalid override [40]: `qualifiers_final_decorator.Derived5.method` cannot override final method defined in `Base5_2`. -qualifiers_final_decorator.py:126:0 Invalid inheritance [39]: `final` cannot be used with non-method functions. +qualifiers_final_decorator.py:64:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method1` cannot override final method defined in `Base2`. +qualifiers_final_decorator.py:68:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method2` cannot override final method defined in `Base2`. +qualifiers_final_decorator.py:72:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method3` cannot override final method defined in `Base2`. +qualifiers_final_decorator.py:83:4 Invalid override [40]: `qualifiers_final_decorator.Derived2.method4` cannot override final method defined in `Base2`. +qualifiers_final_decorator.py:98:4 Incompatible overload [43]: This definition does not have the same decorators as the preceding overload(s). +qualifiers_final_decorator.py:130:4 Inconsistent override [14]: `qualifiers_final_decorator.Derived5.method` overrides method defined in `Base5_2` inconsistently. Could not find parameter `v` in overriding signature. +qualifiers_final_decorator.py:130:4 Invalid override [40]: `qualifiers_final_decorator.Derived5.method` cannot override final method defined in `Base5_2`. +qualifiers_final_decorator.py:138:0 Invalid inheritance [39]: `final` cannot be used with non-method functions. """ conformance_automated = "Fail" errors_diff = """ -Lines 80, 89: Expected error (tag 'Derived3') -Lines 94, 102: Expected error (tag 'Derived4') +Lines 86, 87: Expected error (tag 'method5') +Lines 92, 101: Expected error (tag 'Derived3') +Lines 106, 114: Expected error (tag 'Derived4') Line 51: Unexpected errors ['qualifiers_final_decorator.py:51:4 Incompatible overload [43]: This definition does not have the same decorators as the preceding overload(s).'] """ diff --git a/conformance/results/pyre/version.toml b/conformance/results/pyre/version.toml index 94de3055..be241112 100644 --- a/conformance/results/pyre/version.toml +++ b/conformance/results/pyre/version.toml @@ -1,2 +1,2 @@ version = "pyre 0.9.23" -test_duration = 7.3 +test_duration = 10.0 diff --git a/conformance/results/pyright/aliases_explicit.toml b/conformance/results/pyright/aliases_explicit.toml index a1e82c9e..5948d8ab 100644 --- a/conformance/results/pyright/aliases_explicit.toml +++ b/conformance/results/pyright/aliases_explicit.toml @@ -10,25 +10,25 @@ aliases_explicit.py:79:21 - error: Invalid expression form for type alias defini aliases_explicit.py:79:21 - error: Call expression not allowed in type expression (reportInvalidTypeForm) aliases_explicit.py:80:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:80:21 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_explicit.py:80:21 - error: Expected class but received "list[Unknown]" (reportGeneralTypeIssues) aliases_explicit.py:81:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:81:21 - error: Tuple expression not allowed in type expression -  Use tuple[T1, ..., Tn] to indicate a tuple type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use tuple[T1, ..., Tn] to indicate a tuple type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_explicit.py:82:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:82:21 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_explicit.py:82:21 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) aliases_explicit.py:83:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:83:21 - error: Dictionary expression not allowed in type expression -  Use Dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) +  Use dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) aliases_explicit.py:83:21 - error: Expected class but received "dict[str, Unknown]" (reportGeneralTypeIssues) aliases_explicit.py:83:28 - error: "b" is not defined (reportUndefinedVariable) aliases_explicit.py:84:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:84:21 - error: Call expression not allowed in type expression (reportInvalidTypeForm) aliases_explicit.py:85:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) aliases_explicit.py:85:21 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_explicit.py:85:21 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) aliases_explicit.py:85:27 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) aliases_explicit.py:86:21 - error: Invalid expression form for type alias definition (reportInvalidTypeForm) diff --git a/conformance/results/pyright/aliases_type_statement.toml b/conformance/results/pyright/aliases_type_statement.toml index 4556366e..34269c47 100644 --- a/conformance/results/pyright/aliases_type_statement.toml +++ b/conformance/results/pyright/aliases_type_statement.toml @@ -14,20 +14,20 @@ aliases_type_statement.py:31:22 - error: Argument of type "TypeAliasType" cannot     "TypeAliasType" is not assignable to "tuple[_ClassInfo, ...]" (reportArgumentType) aliases_type_statement.py:37:22 - error: Call expression not allowed in type expression (reportInvalidTypeForm) aliases_type_statement.py:38:22 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_type_statement.py:38:22 - error: Expected class but received "list[Unknown]" (reportGeneralTypeIssues) aliases_type_statement.py:39:22 - error: Tuple expression not allowed in type expression -  Use tuple[T1, ..., Tn] to indicate a tuple type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use tuple[T1, ..., Tn] to indicate a tuple type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_type_statement.py:40:22 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_type_statement.py:40:22 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) aliases_type_statement.py:41:22 - error: Dictionary expression not allowed in type expression -  Use Dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) +  Use dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) aliases_type_statement.py:41:22 - error: Expected class but received "dict[str, Unknown]" (reportGeneralTypeIssues) aliases_type_statement.py:41:29 - error: "b" is not defined (reportUndefinedVariable) aliases_type_statement.py:42:22 - error: Call expression not allowed in type expression (reportInvalidTypeForm) aliases_type_statement.py:43:22 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_type_statement.py:43:22 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) aliases_type_statement.py:43:28 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) aliases_type_statement.py:44:22 - error: Ternary expression not allowed in type expression (reportInvalidTypeForm) diff --git a/conformance/results/pyright/aliases_typealiastype.toml b/conformance/results/pyright/aliases_typealiastype.toml index 64ebf8cf..610c1a96 100644 --- a/conformance/results/pyright/aliases_typealiastype.toml +++ b/conformance/results/pyright/aliases_typealiastype.toml @@ -19,7 +19,7 @@ aliases_typealiastype.py:56:42 - error: Expected class but received "dict[str, U aliases_typealiastype.py:56:49 - error: "b" is not defined (reportUndefinedVariable) aliases_typealiastype.py:57:42 - error: Call expression not allowed in type expression (reportInvalidTypeForm) aliases_typealiastype.py:58:42 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) aliases_typealiastype.py:58:42 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) aliases_typealiastype.py:58:48 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) aliases_typealiastype.py:59:42 - error: Ternary expression not allowed in type expression (reportInvalidTypeForm) diff --git a/conformance/results/pyright/annotations_forward_refs.toml b/conformance/results/pyright/annotations_forward_refs.toml index 29709674..ca35b5bb 100644 --- a/conformance/results/pyright/annotations_forward_refs.toml +++ b/conformance/results/pyright/annotations_forward_refs.toml @@ -6,19 +6,19 @@ annotations_forward_refs.py:24:7 - error: Union syntax cannot be used with strin annotations_forward_refs.py:25:13 - error: Union syntax cannot be used with string operand; use quotes around entire expression (reportGeneralTypeIssues) annotations_forward_refs.py:41:10 - error: Call expression not allowed in type expression (reportInvalidTypeForm) annotations_forward_refs.py:42:10 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_forward_refs.py:42:10 - error: Expected class but received "list[Unknown]" (reportGeneralTypeIssues) annotations_forward_refs.py:43:10 - error: Tuple expression not allowed in type expression -  Use tuple[T1, ..., Tn] to indicate a tuple type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use tuple[T1, ..., Tn] to indicate a tuple type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_forward_refs.py:44:10 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_forward_refs.py:44:10 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) annotations_forward_refs.py:45:10 - error: Dictionary expression not allowed in type expression -  Use Dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) +  Use dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) annotations_forward_refs.py:45:10 - error: Expected class but received "dict[Unknown, Unknown]" (reportGeneralTypeIssues) annotations_forward_refs.py:46:10 - error: Call expression not allowed in type expression (reportInvalidTypeForm) annotations_forward_refs.py:47:10 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_forward_refs.py:47:10 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) annotations_forward_refs.py:47:16 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) annotations_forward_refs.py:48:10 - error: Ternary expression not allowed in type expression (reportInvalidTypeForm) diff --git a/conformance/results/pyright/annotations_typeexpr.toml b/conformance/results/pyright/annotations_typeexpr.toml index 5504e946..e9e3fdca 100644 --- a/conformance/results/pyright/annotations_typeexpr.toml +++ b/conformance/results/pyright/annotations_typeexpr.toml @@ -2,19 +2,19 @@ conformant = "Pass" output = """ annotations_typeexpr.py:88:9 - error: Call expression not allowed in type expression (reportInvalidTypeForm) annotations_typeexpr.py:89:9 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_typeexpr.py:89:9 - error: Expected class but received "list[Unknown]" (reportGeneralTypeIssues) annotations_typeexpr.py:90:9 - error: Tuple expression not allowed in type expression -  Use tuple[T1, ..., Tn] to indicate a tuple type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use tuple[T1, ..., Tn] to indicate a tuple type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_typeexpr.py:91:9 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_typeexpr.py:91:9 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) annotations_typeexpr.py:92:9 - error: Dictionary expression not allowed in type expression -  Use Dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) +  Use dict[T1, T2] to indicate a dictionary type (reportInvalidTypeForm) annotations_typeexpr.py:92:9 - error: Expected class but received "dict[Unknown, Unknown]" (reportGeneralTypeIssues) annotations_typeexpr.py:93:9 - error: Call expression not allowed in type expression (reportInvalidTypeForm) annotations_typeexpr.py:94:9 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) annotations_typeexpr.py:94:9 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) annotations_typeexpr.py:94:15 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) annotations_typeexpr.py:95:9 - error: Ternary expression not allowed in type expression (reportInvalidTypeForm) diff --git a/conformance/results/pyright/generics_syntax_declarations.toml b/conformance/results/pyright/generics_syntax_declarations.toml index 25db9152..bc076dc9 100644 --- a/conformance/results/pyright/generics_syntax_declarations.toml +++ b/conformance/results/pyright/generics_syntax_declarations.toml @@ -6,7 +6,7 @@ generics_syntax_declarations.py:32:11 - error: Cannot access attribute "is_integ   Attribute "is_integer" is unknown (reportAttributeAccessIssue) generics_syntax_declarations.py:44:21 - error: TypeVar constraint type cannot be generic (reportGeneralTypeIssues) generics_syntax_declarations.py:48:17 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) generics_syntax_declarations.py:48:17 - error: Expected class but received "list[Unknown]" (reportGeneralTypeIssues) generics_syntax_declarations.py:60:17 - error: TypeVar must have at least two constrained types (reportGeneralTypeIssues) generics_syntax_declarations.py:64:17 - error: TypeVar must have at least two constrained types (reportGeneralTypeIssues) diff --git a/conformance/results/pyright/generics_variance_inference.toml b/conformance/results/pyright/generics_variance_inference.toml index 5c0f32e2..9a378ad6 100644 --- a/conformance/results/pyright/generics_variance_inference.toml +++ b/conformance/results/pyright/generics_variance_inference.toml @@ -23,12 +23,10 @@ generics_variance_inference.py:58:35 - error: Type "ShouldBeCovariant3[float]" i   "ShouldBeCovariant3[float]" is not assignable to "ShouldBeCovariant3[int]"     Type parameter "T@ShouldBeCovariant3" is covariant, but "float" is not a subtype of "int"       "float" is not assignable to "int" (reportAssignmentType) -generics_variance_inference.py:66:36 - error: Type "ShouldBeCovariant4[int]" is not assignable to declared type "ShouldBeCovariant4[float]" -  "ShouldBeCovariant4[int]" is not assignable to "ShouldBeCovariant4[float]" -    Type parameter "T@ShouldBeCovariant4" is invariant, but "int" is not the same as "float" (reportAssignmentType) generics_variance_inference.py:67:34 - error: Type "ShouldBeCovariant4[float]" is not assignable to declared type "ShouldBeCovariant4[int]"   "ShouldBeCovariant4[float]" is not assignable to "ShouldBeCovariant4[int]" -    Type parameter "T@ShouldBeCovariant4" is invariant, but "float" is not the same as "int" (reportAssignmentType) +    Type parameter "T@ShouldBeCovariant4" is covariant, but "float" is not a subtype of "int" +      "float" is not assignable to "int" (reportAssignmentType) generics_variance_inference.py:80:34 - error: Type "ShouldBeCovariant5[float]" is not assignable to declared type "ShouldBeCovariant5[int]"   "ShouldBeCovariant5[float]" is not assignable to "ShouldBeCovariant5[int]"     Type parameter "T@ShouldBeCovariant5" is covariant, but "float" is not a subtype of "int" @@ -82,7 +80,6 @@ generics_variance_inference.py:194:37 - error: Type "ShouldBeContravariant2[int]     Type parameter "T@ShouldBeContravariant2" is contravariant, but "int" is not a supertype of "float"       "float" is not assignable to "int" (reportAssignmentType) """ -conformance_automated = "Fail" +conformance_automated = "Pass" errors_diff = """ -Line 66: Unexpected errors ['generics_variance_inference.py:66:36 - error: Type "ShouldBeCovariant4[int]" is not assignable to declared type "ShouldBeCovariant4[float]"'] """ diff --git a/conformance/results/pyright/qualifiers_annotated.toml b/conformance/results/pyright/qualifiers_annotated.toml index b8c271f0..c7f60d82 100644 --- a/conformance/results/pyright/qualifiers_annotated.toml +++ b/conformance/results/pyright/qualifiers_annotated.toml @@ -9,7 +9,7 @@ qualifiers_annotated.py:46:17 - error: Dictionary expression not allowed in type qualifiers_annotated.py:46:24 - error: "b" is not defined (reportUndefinedVariable) qualifiers_annotated.py:47:17 - error: Call expression not allowed in type expression (reportInvalidTypeForm) qualifiers_annotated.py:48:17 - error: List expression not allowed in type expression -  Use List[T] to indicate a list type or Union[T1, T2] to indicate a union type (reportInvalidTypeForm) +  Use list[T] to indicate a list type or T1 | T2 to indicate a union type (reportInvalidTypeForm) qualifiers_annotated.py:48:17 - error: Expected class but received "list[type[int]]" (reportGeneralTypeIssues) qualifiers_annotated.py:48:23 - error: Expected class but received "Literal[0]" (reportGeneralTypeIssues) qualifiers_annotated.py:49:17 - error: Ternary expression not allowed in type expression (reportInvalidTypeForm) diff --git a/conformance/results/pyright/qualifiers_final_decorator.toml b/conformance/results/pyright/qualifiers_final_decorator.toml index 6a315650..ab5e3697 100644 --- a/conformance/results/pyright/qualifiers_final_decorator.toml +++ b/conformance/results/pyright/qualifiers_final_decorator.toml @@ -1,21 +1,22 @@ -conformant = "Pass" +conformant = "Partial" output = """ qualifiers_final_decorator.py:8:6 - warning: Import "_qualifiers_final_decorator" could not be resolved from source (reportMissingModuleSource) qualifiers_final_decorator.py:21:16 - error: Base class "Base1" is marked final and cannot be subclassed (reportGeneralTypeIssues) -qualifiers_final_decorator.py:56:9 - error: Method "method1" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:60:9 - error: Method "method2" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:64:9 - error: Method "method3" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:75:9 - error: Method "method4" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:86:9 - error: Overload for "method" is marked @final but implementation is not (reportInconsistentOverload) -qualifiers_final_decorator.py:89:9 - error: Method "method" cannot override final method defined in class "Base3" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:102:9 - error: Method "method" cannot override final method defined in class "Base4" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:118:9 - error: Method "method" cannot override final method defined in class "Base5_2" (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:118:9 - error: Method "method" overrides class "Base5_2" in an incompatible manner +qualifiers_final_decorator.py:64:9 - error: Method "method1" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:68:9 - error: Method "method2" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:72:9 - error: Method "method3" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:83:9 - error: Method "method4" cannot override final method defined in class "Base2" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:98:9 - error: @final decorator should be applied only to the implementation (reportInconsistentOverload) +qualifiers_final_decorator.py:101:9 - error: Method "method" cannot override final method defined in class "Base3" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:114:9 - error: Method "method" cannot override final method defined in class "Base4" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:130:9 - error: Method "method" cannot override final method defined in class "Base5_2" (reportIncompatibleMethodOverride) +qualifiers_final_decorator.py:130:9 - error: Method "method" overrides class "Base5_2" in an incompatible manner   Positional parameter count mismatch; base method has 2, but override has 1   Parameter 2 mismatch: base parameter "v" is keyword parameter, override parameter is position-only (reportIncompatibleMethodOverride) -qualifiers_final_decorator.py:126:5 - error: Function "func1" cannot be marked @final because it is not a method (reportGeneralTypeIssues) +qualifiers_final_decorator.py:138:5 - error: Function "func1" cannot be marked @final because it is not a method (reportGeneralTypeIssues) """ -conformance_automated = "Pass" +conformance_automated = "Fail" errors_diff = """ +Lines 86, 87: Expected error (tag 'method5') """ ignore_errors = ["reportMissingModuleSource"] diff --git a/conformance/results/pyright/version.toml b/conformance/results/pyright/version.toml index e8e963b7..bd8e50c8 100644 --- a/conformance/results/pyright/version.toml +++ b/conformance/results/pyright/version.toml @@ -1,2 +1,2 @@ -version = "pyright 1.1.391" -test_duration = 1.2 +version = "pyright 1.1.393" +test_duration = 1.8 diff --git a/conformance/results/pytype/qualifiers_final_decorator.toml b/conformance/results/pytype/qualifiers_final_decorator.toml index 3910ac78..16b45b10 100644 --- a/conformance/results/pytype/qualifiers_final_decorator.toml +++ b/conformance/results/pytype/qualifiers_final_decorator.toml @@ -21,7 +21,7 @@ qualifiers_final_decorator.py:52:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m return 0 \u001b[1m\u001b[31m~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:55:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method4, defined in base class Base2 [final-error] +qualifiers_final_decorator.py:63:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method5, defined in base class Base2 [final-error] class Derived2(Base2): \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m @@ -68,7 +68,15 @@ class Derived2(Base2): return 0 \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:55:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method3, defined in base class Base2 [final-error] +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @property # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method5(self) -> bool: # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return True +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +qualifiers_final_decorator.py:63:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method4, defined in base class Base2 [final-error] class Derived2(Base2): \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m @@ -115,7 +123,15 @@ class Derived2(Base2): return 0 \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:55:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method2, defined in base class Base2 [final-error] +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @property # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method5(self) -> bool: # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return True +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +qualifiers_final_decorator.py:63:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method3, defined in base class Base2 [final-error] class Derived2(Base2): \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m @@ -162,7 +178,15 @@ class Derived2(Base2): return 0 \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:55:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method1, defined in base class Base2 [final-error] +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @property # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method5(self) -> bool: # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return True +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +qualifiers_final_decorator.py:63:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method2, defined in base class Base2 [final-error] class Derived2(Base2): \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m @@ -209,22 +233,85 @@ class Derived2(Base2): return 0 \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:76:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method4: bad return type [bad-return-type] +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @property # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method5(self) -> bool: # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return True +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +qualifiers_final_decorator.py:63:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived2 overrides final method method1, defined in base class Base2 [final-error] + +class Derived2(Base2): +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method1(self) -> None: # E +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + pass +\u001b[1m\u001b[31m~~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @classmethod # E[method2] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method2(cls) -> None: # E[method2] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + pass +\u001b[1m\u001b[31m~~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @staticmethod # E[method3] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method3() -> None: # E[method3] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + pass +\u001b[1m\u001b[31m~~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @overload # E[method4] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method4(self, x: int) -> int: +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + ... +\u001b[1m\u001b[31m~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @overload +\u001b[1m\u001b[31m~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method4(self, x: str) -> str: +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + ... +\u001b[1m\u001b[31m~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + def method4(self, x: int | str) -> int | str: # E[method4] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return 0 +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +\u001b[1m\u001b[31m\u001b[39m\u001b[0m + @property # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + def method5(self) -> bool: # E[method5] +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + return True +\u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m + +qualifiers_final_decorator.py:84:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method4: bad return type [bad-return-type] return 0 \u001b[1m\u001b[31m~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:90:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method: bad return type [bad-return-type] +qualifiers_final_decorator.py:102:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method: bad return type [bad-return-type] return 0 \u001b[1m\u001b[31m~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:103:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method: bad return type [bad-return-type] +qualifiers_final_decorator.py:115:16: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in method: bad return type [bad-return-type] return 0 \u001b[1m\u001b[31m~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:117:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived5 overrides final method method, defined in base class Base5_2 [final-error] +qualifiers_final_decorator.py:129:1: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Class Derived5 overrides final method method, defined in base class Base5_2 [final-error] class Derived5(Base5_1, Base5_2): \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m @@ -233,14 +320,14 @@ class Derived5(Base5_1, Base5_2): ... \u001b[1m\u001b[31m~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:118:5: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in Derived5: Overriding method signature mismatch [signature-mismatch] +qualifiers_final_decorator.py:130:5: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in Derived5: Overriding method signature mismatch [signature-mismatch] def method(self) -> None: # E \u001b[1m\u001b[31m~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\u001b[39m\u001b[0m ... \u001b[1m\u001b[31m~~~~~~~~~~~\u001b[39m\u001b[0m -qualifiers_final_decorator.py:125:2: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Cannot apply @final decorator to func1 [final-error] +qualifiers_final_decorator.py:137:2: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m: in : Cannot apply @final decorator to func1 [final-error] @final # E[func]: not allowed on non-method function. \u001b[1m\u001b[31m~~~~~\u001b[39m\u001b[0m @@ -248,18 +335,19 @@ qualifiers_final_decorator.py:125:2: \u001b[1m\u001b[31merror\u001b[39m\u001b[0m """ conformance_automated = "Fail" errors_diff = """ -Line 56: Expected 1 errors -Lines 59, 60: Expected error (tag 'method2') -Lines 63, 64: Expected error (tag 'method3') -Lines 67, 75: Expected error (tag 'method4') -Lines 80, 89: Expected error (tag 'Derived3') -Lines 84, 85, 86: Expected error (tag 'Derived3-2') -Lines 94, 102: Expected error (tag 'Derived4') +Line 64: Expected 1 errors +Lines 67, 68: Expected error (tag 'method2') +Lines 71, 72: Expected error (tag 'method3') +Lines 75, 83: Expected error (tag 'method4') +Lines 86, 87: Expected error (tag 'method5') +Lines 92, 101: Expected error (tag 'Derived3') +Lines 96, 97, 98: Expected error (tag 'Derived3-2') +Lines 106, 114: Expected error (tag 'Derived4') Line 8: Unexpected errors ["qualifiers_final_decorator.py:8:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Couldn't import pyi for '_qualifiers_final_decorator' [pyi-error]"] Line 52: Unexpected errors ['qualifiers_final_decorator.py:52:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method4: bad return type [bad-return-type]'] -Line 55: Unexpected errors ['qualifiers_final_decorator.py:55:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method4, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:55:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method3, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:55:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method2, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:55:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method1, defined in base class Base2 [final-error]'] -Line 76: Unexpected errors ['qualifiers_final_decorator.py:76:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method4: bad return type [bad-return-type]'] -Line 90: Unexpected errors ['qualifiers_final_decorator.py:90:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method: bad return type [bad-return-type]'] -Line 103: Unexpected errors ['qualifiers_final_decorator.py:103:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method: bad return type [bad-return-type]'] -Line 117: Unexpected errors ['qualifiers_final_decorator.py:117:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived5 overrides final method method, defined in base class Base5_2 [final-error]'] +Line 63: Unexpected errors ['qualifiers_final_decorator.py:63:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method5, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:63:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method4, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:63:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method3, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:63:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method2, defined in base class Base2 [final-error]', 'qualifiers_final_decorator.py:63:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived2 overrides final method method1, defined in base class Base2 [final-error]'] +Line 84: Unexpected errors ['qualifiers_final_decorator.py:84:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method4: bad return type [bad-return-type]'] +Line 102: Unexpected errors ['qualifiers_final_decorator.py:102:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method: bad return type [bad-return-type]'] +Line 115: Unexpected errors ['qualifiers_final_decorator.py:115:16: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in method: bad return type [bad-return-type]'] +Line 129: Unexpected errors ['qualifiers_final_decorator.py:129:1: \\x1b[1m\\x1b[31merror\\x1b[39m\\x1b[0m: in : Class Derived5 overrides final method method, defined in base class Base5_2 [final-error]'] """ diff --git a/conformance/results/pytype/version.toml b/conformance/results/pytype/version.toml index 94cd5eee..e0712e9c 100644 --- a/conformance/results/pytype/version.toml +++ b/conformance/results/pytype/version.toml @@ -1,2 +1,2 @@ version = "pytype 2024.10.11" -test_duration = 37.2 +test_duration = 76.6 diff --git a/conformance/results/results.html b/conformance/results/results.html index e388ee38..05364b19 100644 --- a/conformance/results/results.html +++ b/conformance/results/results.html @@ -158,17 +158,17 @@

Python Type System Conformance Test Results

- -
 
mypy 1.14.0
-
1.6sec
+
mypy 1.14.1
+
3.3sec
pyright 1.1.391
-
1.2sec
+
pyright 1.1.393
+
1.8sec
pyre 0.9.23
-
7.3sec
+
10.0sec
pytype 2024.10.11
-
37.2sec
+
76.6sec
diff --git a/conformance/tests/qualifiers_final_decorator.py b/conformance/tests/qualifiers_final_decorator.py index 3523ae53..88417505 100644 --- a/conformance/tests/qualifiers_final_decorator.py +++ b/conformance/tests/qualifiers_final_decorator.py @@ -51,6 +51,14 @@ def method4(self, x: str) -> str: def method4(self, x: int | str) -> int | str: return 0 + # > @final may be chained with decorators that return a non-function, like a + # property descriptor. + + @final + @property + def method5(self) -> int: + return 0 + class Derived2(Base2): def method1(self) -> None: # E @@ -75,6 +83,10 @@ def method4(self, x: str) -> str: def method4(self, x: int | str) -> int | str: # E[method4] return 0 + @property # E[method5] + def method5(self) -> bool: # E[method5] + return True + class Derived3(Base3): @overload # E[Derived3] diff --git a/docs/spec/qualifiers.rst b/docs/spec/qualifiers.rst index 7ba4d9f4..a4c00ebf 100644 --- a/docs/spec/qualifiers.rst +++ b/docs/spec/qualifiers.rst @@ -66,6 +66,22 @@ implementation (or on the first overload, for stubs):: def method(self, x=None): ... +The ``@final`` decorator can be combined with previous decorators, like +``@property``. Example:: + + from typing import final + + class Base: + @final + @property + def foo(self) -> None: + ... + + class Derived(Base): + @property + def foo(self) -> None: # Error: Cannot override final attribute "foo" + ... + It is an error to use ``@final`` on a non-method function. .. _`uppercase-final`: