From f78219153f5ef4438026a77565bceb8fc8ef6449 Mon Sep 17 00:00:00 2001 From: Michael Lee Date: Tue, 4 Sep 2018 13:07:25 -0700 Subject: [PATCH] Remove the 'rop will not be called' error message https://github.com/python/mypy/pull/5475 introduced a new type of error message ("__rop__ will not be called when evaluating 'a + b'...") that triggers when the user tries evaluating expressions like `foo + foo` where `foo` does not contain an `__add__` method that accepts a value of the same type, but *does* contain an `__radd__` method that does. This pull request removes that error message on the grounds that it's too cryptic and unlikely to be helpful to most mypy users. That error message is useful mainly for people developing libraries containing custom numeric types (or libraries that appropriate operators to create custom DSLs) -- however, most people are not library creators and so will not find this error message useful. --- mypy/checkexpr.py | 11 ----------- mypy/messages.py | 16 ---------------- test-data/unit/check-classes.test | 9 +++------ 3 files changed, 3 insertions(+), 33 deletions(-) diff --git a/mypy/checkexpr.py b/mypy/checkexpr.py index 743a77e74260..798f98915660 100644 --- a/mypy/checkexpr.py +++ b/mypy/checkexpr.py @@ -1909,7 +1909,6 @@ def lookup_definer(typ: Instance, attr_name: str) -> Optional[str]: # We store the determined order inside the 'variants_raw' variable, # which records tuples containing the method, base type, and the argument. - warn_about_uncalled_reverse_operator = False bias_right = is_proper_subtype(right_type, left_type) if op_name in nodes.op_methods_that_shortcut and is_same_type(left_type, right_type): # When we do "A() + A()", for example, Python will only call the __add__ method, @@ -1921,8 +1920,6 @@ def lookup_definer(typ: Instance, attr_name: str) -> Optional[str]: variants_raw = [ (left_op, left_type, right_expr) ] - if right_op is not None: - warn_about_uncalled_reverse_operator = True elif (is_subtype(right_type, left_type) and isinstance(left_type, Instance) and isinstance(right_type, Instance) @@ -2010,14 +2007,6 @@ def lookup_definer(typ: Instance, attr_name: str) -> Optional[str]: return result self.msg.add_errors(errors[0]) - if warn_about_uncalled_reverse_operator: - self.msg.reverse_operator_method_never_called( - nodes.op_methods_to_symbols[op_name], - op_name, - right_type, - rev_op_name, - context, - ) if len(results) == 1: return results[0] else: diff --git a/mypy/messages.py b/mypy/messages.py index 1b277c68f25a..df225dcde0a5 100644 --- a/mypy/messages.py +++ b/mypy/messages.py @@ -1003,22 +1003,6 @@ def overloaded_signatures_ret_specific(self, index: int, context: Context) -> No self.fail('Overloaded function implementation cannot produce return type ' 'of signature {}'.format(index), context) - def reverse_operator_method_never_called(self, - op: str, - forward_method: str, - reverse_type: Type, - reverse_method: str, - context: Context) -> None: - msg = "{rfunc} will not be called when evaluating '{cls} {op} {cls}': must define {ffunc}" - self.note( - msg.format( - op=op, - ffunc=forward_method, - rfunc=reverse_method, - cls=self.format_bare(reverse_type), - ), - context=context) - def operator_method_signatures_overlap( self, reverse_class: TypeInfo, reverse_method: str, forward_class: Type, forward_method: str, context: Context) -> None: diff --git a/test-data/unit/check-classes.test b/test-data/unit/check-classes.test index 54d43097ff30..e042cc4faad1 100644 --- a/test-data/unit/check-classes.test +++ b/test-data/unit/check-classes.test @@ -1616,8 +1616,7 @@ class B(A): pass # Note: This is a runtime error. If we run x.__add__(y) # where x and y are *not* the same type, Python will not try # calling __radd__. -A() + A() # E: Unsupported operand types for + ("A" and "A") \ - # N: __radd__ will not be called when evaluating 'A + A': must define __add__ +A() + A() # E: Unsupported operand types for + ("A" and "A") # Here, Python *will* call __radd__(...) reveal_type(B() + A()) # E: Revealed type is '__main__.A' @@ -1733,8 +1732,7 @@ class A: def __radd__(self, other: 'A') -> int: ... # Note: Python only tries calling __add__ and never __radd__, even though it's present -A() + A() # E: Unsupported left operand type for + ("A") \ - # N: __radd__ will not be called when evaluating 'A + A': must define __add__ +A() + A() # E: Unsupported left operand type for + ("A") [case testReverseOperatorOrderingCase2] class A: @@ -2006,8 +2004,7 @@ reveal_type(FractionChild() + FractionChild()) # E: Revealed type is 'builtins. # Runtime error: we try calling __add__, it doesn't match, and we don't try __radd__ since # the LHS and the RHS are not the same. -Fraction() + Fraction() # E: Unsupported operand types for + ("Fraction" and "Fraction") \ - # N: __radd__ will not be called when evaluating 'Fraction + Fraction': must define __add__ +Fraction() + Fraction() # E: Unsupported operand types for + ("Fraction" and "Fraction") [case testReverseOperatorTypeType] from typing import TypeVar, Type