Repository navigation
Conversation
When the left operand lacks the forward comparison method, the error was rendered from the reflected method name (e.g. `x >= 0` reported ` <= ` instead of ` >= `); report the operator as written, with operands in source order. Fixes python#22316.
Contributor
|
Diff from mypy_primer, showing the effect of this PR on open source code: spark (https://github.com/apache/spark)
- python/pyspark/pandas/groupby.py:756: error: Unsupported operand types for >= ("int" and "Number") [operator]
+ python/pyspark/pandas/groupby.py:756: error: Unsupported operand types for <= ("Number" and "int") [operator]
prefect (https://github.com/PrefectHQ/prefect)
- src/prefect/cli/work_queue.py:742: error: Unsupported operand types for > ("datetime" and "None") [operator]
+ src/prefect/cli/work_queue.py:742: error: Unsupported operand types for < ("None" and "datetime") [operator]
discord.py (https://github.com/Rapptz/discord.py)
- discord/ext/tasks/__init__.py:232: error: Unsupported operand types for >= ("datetime" and "None") [operator]
+ discord/ext/tasks/__init__.py:232: error: Unsupported operand types for <= ("None" and "datetime") [operator]
pyodide (https://github.com/pyodide/pyodide)
- pyodide-build/pyodide_build/tests/test_xbuildenv.py:398: error: Unsupported operand types for <= ("str" and "None") [operator]
+ pyodide-build/pyodide_build/tests/test_xbuildenv.py:398: error: Unsupported operand types for >= ("None" and "str") [operator]
- pyodide-build/pyodide_build/tests/test_xbuildenv.py:401: error: Unsupported operand types for <= ("str" and "None") [operator]
+ pyodide-build/pyodide_build/tests/test_xbuildenv.py:401: error: Unsupported operand types for >= ("None" and "str") [operator]
cvxpy (https://github.com/cvxpy/cvxpy)
- cvxpy/expressions/expression.py:424: error: Unsupported operand types for < ("int" and "generic[Any]") [operator]
+ cvxpy/expressions/expression.py:424: error: Unsupported operand types for > ("generic[Any]" and "int") [operator]
- cvxpy/expressions/expression.py:424: error: Unsupported operand types for < ("int" and "sparray[Any, tuple[Any, ...]]") [operator]
+ cvxpy/expressions/expression.py:424: error: Unsupported operand types for > ("sparray[Any, tuple[Any, ...]]" and "int") [operator]
- cvxpy/expressions/expression.py:424: error: Unsupported operand types for < ("int" and "complex") [operator]
+ cvxpy/expressions/expression.py:424: error: Unsupported operand types for > ("complex" and "int") [operator]
- cvxpy/expressions/constants/constant.py:134: error: Unsupported operand types for < ("int" and "None") [operator]
+ cvxpy/expressions/constants/constant.py:134: error: Unsupported operand types for > ("None" and "int") [operator]
- cvxpy/utilities/power_tools.py:175: error: Unsupported operand types for < ("int" and "Integral") [operator]
+ cvxpy/utilities/power_tools.py:175: error: Unsupported operand types for > ("Integral" and "int") [operator]
- cvxpy/utilities/power_tools.py:197: error: Unsupported operand types for <= ("int" and "Integral") [operator]
+ cvxpy/utilities/power_tools.py:197: error: Unsupported operand types for >= ("Integral" and "int") [operator]
jax (https://github.com/google/jax)
- jax/_src/lax/slicing.py:3801: error: Unsupported operand types for > ("int" and "complex") [operator]
+ jax/_src/lax/slicing.py:3801: error: Unsupported operand types for < ("complex" and "int") [operator]
- jax/_src/numpy/indexing.py:364: error: Unsupported operand types for > ("int" and "slice[Any, Any, Any]") [operator]
+ jax/_src/numpy/indexing.py:364: error: Unsupported operand types for < ("slice[Any, Any, Any]" and "int") [operator]
- jax/_src/numpy/indexing.py:364: error: Unsupported operand types for > ("int" and "EllipsisType") [operator]
- jax/_src/numpy/indexing.py:364: error: Unsupported operand types for > ("int" and "None") [operator]
+ jax/_src/numpy/indexing.py:364: error: Unsupported operand types for < ("EllipsisType" and "int") [operator]
- jax/_src/numpy/indexing.py:364: error: Unsupported operand types for > ("int" and "Sequence[int | integer[Any]]") [operator]
+ jax/_src/numpy/indexing.py:364: error: Unsupported operand types for < ("None" and "int") [operator]
+ jax/_src/numpy/indexing.py:364: error: Unsupported operand types for < ("Sequence[int | integer[Any]]" and "int") [operator]
- jax/experimental/mosaic/gpu/fragmented_array.py:5547: error: Unsupported operand types for < ("int" and "object") [operator]
+ jax/experimental/mosaic/gpu/fragmented_array.py:5547: error: Unsupported operand types for > ("object" and "int") [operator]
- jax/experimental/mosaic/gpu/fragmented_array.py:5657: error: Unsupported operand types for < ("int" and "object") [operator]
+ jax/experimental/mosaic/gpu/fragmented_array.py:5657: error: Unsupported operand types for > ("object" and "int") [operator]
apprise (https://github.com/caronc/apprise)
- apprise/persistent_store.py:1528: error: Unsupported operand types for > ("datetime" and "None") [operator]
+ apprise/persistent_store.py:1528: error: Unsupported operand types for < ("None" and "datetime") [operator]
- apprise/plugins/amqp/base.py:414: error: Unsupported operand types for >= ("int" and "object") [operator]
+ apprise/plugins/amqp/base.py:414: error: Unsupported operand types for <= ("object" and "int") [operator]
- apprise/plugins/mobilemessage.py:255: error: Unsupported operand types for >= ("int" and "object") [operator]
+ apprise/plugins/mobilemessage.py:255: error: Unsupported operand types for <= ("object" and "int") [operator]
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fix flipped operator in comparison error message
Fixes #22316.
def f(x: int | None) -> bool: return x >= 0reportedeven though the code uses
>=. The same mirroring affected all fourordering operators (
>=was reported as<=,<=as>=,>as<,<as>).Root cause
When the left operand has no forward comparison method (here
NoneTypehas no
__ge__),check_op_reversiblefalls back to the reflected callon the right operand (
int.__le__(x)), and the error is rendered fromthe callee's method name alone in
MessageBuilder.incompatible_argument.The renderer cannot tell a reflected
__le__call apart from a genuine<=, so it reports the reflected operator with the operands inreflected order.
Fix
check_op_reversiblenow records the operator as written in the sourcecode while trying each candidate method, using a small
MessageBuilder.operator_context(the same push/pop pattern as theexisting
disable_type_names).incompatible_argumentuses that contextfor the four ordering methods (
__lt__,__le__,__gt__,__ge__):the symbol is taken from the source operator, and the operands are
reported in source order when the failing call was the reflected one.
Forward calls,
__r*__operators,==/!=,in, and the"unsupported left operand" path (when neither method exists) are
unaffected.
One judgment call, following the analysis in the issue: the operands are
reported in source order (
>= ("None" and "int")), matching CPython'sruntime message (
'>=' not supported between instances of 'NoneType' and 'int'), rather than keeping the old reflected order with only thesymbol fixed.
Tests
New regression test
testComparisonOperatorMessageWithNoneintest-data/unit/check-expressions.test(usingfixtures/ops.pyi, whichgives
intits comparison methods). It failed on unmodified code withthe mirrored operators and passes with the fix. The existing assertions
that baked in the mirrored rendering were updated (17 lines across
check-expressions.test,check-incremental.test, andcheck-plugin-attrs.test).Test runs (all with the repo venv):
pytest mypy/test/testcheck.py -k "check-expressions.test or check-plugin-attrs.test": 342 passedpytest mypy/test/testcheck.py -k "check-incremental.test": 359 passed, 4 skippedpytest mypy/test/testcheck.py(full suite): 8317 passed, 27 skipped, 7 xfailedx >= 0now reports>= ("None" and "int"), and the control casex: int; s: str; x >= sstill reports>= ("int" and "str")Note: I used an AI coding assistant while working on this fix, and
verified the change and the tests myself.