-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[ruff
] IO operations performed on closed IO objects (RUF050
)
#15865
base: main
Are you sure you want to change the base?
Conversation
|
code | total | + violation | - violation | + fix | - fix |
---|---|---|---|---|---|
RUF050 | 2 | 2 | 0 | 0 | 0 |
There are a lot of false positives of this kind: with open() as f:
f.read() # A reference to the next `f`
with open() as f: # Same name
...
with open() as f: # Same name
f.write() # A reference to either of the previous `f`s This seems to be a bug in the semantic model rather than a problem with this rule. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for working on this.
As mentioned in the original PR, we have to restrict the rule to objects that are files. This should also help to remove the following false positive
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
ruff
] IO operations performed on closed IO objects (RUF061
)ruff
] IO operations performed on closed IO objects (RUF050
)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm concerned about the examples you mentioned as well as if f
gets deleted.
It seems that the semantic model copies over all references when shadowing an existing binding.
ruff/crates/ruff_linter/src/checkers/ast/mod.rs
Lines 2048 to 2062 in fe516e2
let references = shadowed.references.clone(); | |
let is_global = shadowed.is_global(); | |
let is_nonlocal = shadowed.is_nonlocal(); | |
// If the shadowed binding was global, then this one is too. | |
if is_global { | |
self.semantic.bindings[binding_id].flags |= BindingFlags::GLOBAL; | |
} | |
// If the shadowed binding was non-local, then this one is too. | |
if is_nonlocal { | |
self.semantic.bindings[binding_id].flags |= BindingFlags::NONLOCAL; | |
} | |
self.semantic.bindings[binding_id].references = references; |
I think we have to make the rule shadowed-binding aware and skip over references that come from a shadowed binding.
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
crates/ruff_linter/src/rules/ruff/rules/operation_on_closed_io.rs
Outdated
Show resolved
Hide resolved
I'm not sure how to do this, especially if all references are simply copied over. |
Yeah, me neither. We'd have to look at other rules to see how to handle it. I don't think I've the time right now to do that. Maybe @charliermarsh knows? |
Summary
Resolves #10517.
RUF050
checks for references of IO objects whose binding is created by awith
statement and reports if those references might triggerValueError: I/O operation on closed file
at runtime.It recognizes the following patterns:
f.read()
/_ = f.write
_ in f
for
loops:for _ in f: ...
Test Plan
cargo nextest run
andcargo insta test
.