astral-sh/ruff
在 GitHub 查看F841 treats `except` bindings differently from all other bindings
Open
#16,537 建立於 2025年3月6日
bughelp wanted
描述
Summary
The implementation of unused-variable (F841) is split: except bindings are handled separately in bindings.rs, causing false positives. They should be processed consistently with other bindings.
One false positive occurs when the bound variable is not used within the except block but is used outside it. The fix can change program behavior by suppressing a runtime error. The fix could be beneficial, but it should be marked unsafe like other unused bindings’ fixes.
$ cat >f841_1.py <<'# EOF'
def f():
e = None
try:
1 / 0
except ZeroDivisionError as e:
pass
print(e)
f()
# EOF
$ python f841_1.py 2>&1 | tail -n 1
UnboundLocalError: cannot access local variable 'e' where it is not associated with a value
$ ruff --isolated check --select F841 f841_1.py --fix
Found 1 error (1 fixed, 0 remaining).
$ cat f841_1.py
def f():
e = None
try:
1 / 0
except ZeroDivisionError:
pass
print(e)
f()
$ python f841_1.py
None
Another false positive occurs when the binding is not within a function.
$ cat >f841_2.py <<'# EOF'
e = None
try:
1 / 0
except ZeroDivisionError as e:
pass
print(e)
# EOF
$ python f841_2.py 2>&1 | tail -n 1
NameError: name 'e' is not defined
$ ruff --isolated check --select F841 f841_2.py --fix
Found 1 error (1 fixed, 0 remaining).
$ cat f841_2.py
e = None
try:
1 / 0
except ZeroDivisionError:
pass
print(e)
$ python f841_2.py
None
There are other false positives, but they are all variations on the same theme. They can probably all be fixed by merging the two F841 implementations.
Version
ruff 0.9.9 (091d0af2a 2025-02-28)