-
Notifications
You must be signed in to change notification settings - Fork 13.9k
Not linting irrefutable_let_patterns on let chains #146832
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
base: master
Are you sure you want to change the base?
Not linting irrefutable_let_patterns on let chains #146832
Conversation
This comment was marked as off-topic.
This comment was marked as off-topic.
This comment has been minimized.
This comment has been minimized.
11d320a to
450d0a3
Compare
This comment has been minimized.
This comment has been minimized.
450d0a3 to
0aae158
Compare
This comment has been minimized.
This comment has been minimized.
ce66065 to
e77a3c4
Compare
|
Some changes occurred in match checking cc @Nadrieril The Miri subtree was changed cc @rust-lang/miri |
|
It seems that only modifying |
All the lints seem to be removed in that test, but you'll want to ensure there are tests that cover the edges of what is still linted here. @rustbot author |
|
Reminder, once the PR becomes ready for a review, use |
e77a3c4 to
6425c06
Compare
| // For let chains, don't lint. | ||
| if let [Some((_, refutability))] = chain_refutabilities[..] { | ||
| self.check_single_let(refutability, ex.span); |
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.
but you'll want to ensure there are tests that cover the edges of what is still linted here.
match chain_refutabilities.len() {
0 => "`assert!(self.let_source != LetSource::None)` ensure this case doesn't exist"
2.. => "`if let [Some((_, refutability))] = chain_refutabilities[..]` ensure not checked" // The purpose of this PR: don't check let chains
1 if chain_refutabilities[0].is_none()
=> "A boolean expression at the start of `while let` | `if let` | `else if let`, this case cannot pass syntax analysis"
1 if chain_refutabilities[0].is_some()
=> "There is exactly one let binding in `while let` | `if let` | `else if let` statement, proceed to check"
}
No one answered, but the answer is "add the I-lang-nominated label and wait for the lang team to look at it", which @traviscross did. So there's nothing more to do for you until then :) |
|
Hi, I really hope this PR can be merged before the 1.91 release. Is there any progress now |
That's not possible, master is 1.92 already and 1.91 is beta meaning the latter only accepts patches for stable-to-beta and stable-to-stable regressions (also, 1.91 will be promoted to stable next week). |
|
@rfcbot merge |
|
Team member @joshtriplett has proposed to merge this. The next step is review by the rest of the tagged team members: No concerns currently listed. Once a majority of reviewers approve (and at most 2 approvals are outstanding), this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up! cc @rust-lang/lang-advisors: FCP proposed for lang, please feel free to register concerns. |
| if chain_refutabilities.iter().any(|x| x.is_some()) { | ||
| self.check_let_chain(chain_refutabilities, ex.span); | ||
| // Check only single let binding | ||
| if let [Some((_, refutability))] = chain_refutabilities[..] { |
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.
| if let [Some((_, refutability))] = chain_refutabilities[..] { | |
| if let [Some((_, Irrefutable))] = chain_refutabilities[..] { |
Could go either way, I suppose, but it almost seems worth just doing the rest of the check inline here. It's already checking the "only one" part; maybe it should just check the "irrefutable" part also. Then either check_single_let could be renamed to lint_single_let (since the check has been moved out of it) or perhaps be fully inlined.
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've pushed a new commit addressing this suggestion. Not sure if it meets your expectations
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.
Yes, looks right. With it factored this way, might as well use lint_single_let in check_let as well.
|
@rfcbot reviewed |
07a68e3 to
8e87b4f
Compare
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
| if chain_refutabilities.iter().any(|x| x.is_some()) { | ||
| self.check_let_chain(chain_refutabilities, ex.span); | ||
| // Lint only single irrefutable let binding. | ||
| if let [Some((_, Irrefutable))] = chain_refutabilities[..] { |
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.
What if there are multiple bindings, all irrefutable?
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.
Not linting as long as it is chains. In #139369 , people have nearly reached a consensus on this point.
This comment has been minimized.
This comment has been minimized.
44aa5a9 to
2ef07fd
Compare
This comment has been minimized.
This comment has been minimized.
90b9a03 to
cd61dc0
Compare
cd61dc0 to
cdf1cde
Compare
Description
this PR makes the lint
irrefutable_let_patternsnot check forlet chains,only check for single
if let,while let, andif let guard.Motivation
Since
let chainswere stabilized, the following code has become common:This code naturally expresses "please call that function and then do something if the return value satisfies a condition".
Putting the let binding outside the if would be bad as then it remains in scope after the if, which is not the intent.
Current Output:
Another common case is progressively destructuring a struct with enum fields, or an enum with struct variants:
Current Output:
To avoid the warning, the readability would be much worse:
related issue
possible questions
Moving the irrefutable pattern at the head of the chain out of it would cause a variable that was intended to be temporary to remain in scope, so we remove it.
However, should we keep the check for moving the irrefutable pattern at the tail into the body?
Should we still lint
entire chain is made up of irrefutable let?This is my first time contributing non-documentation code to Rust. If there are any irregularities, please feel free to point them out.
: )