Skip to content

Fix Lint/ElseLayout when using multi-branch statements #10147

@bkuhlmann

Description

@bkuhlmann

Expected behavior

With the latest release of Rubocop, I'm noticing a behavioral change that I think is a bug or at least an oddity. This issue is related to this original issue. If I understand the intent of the original issue, I think it was intended for single if and else statement -- which makes sense -- but I think this breaks when used in an if..elsif..else statement?

Actual behavior

I'm seeing Lint/ElseLayout issues with single line else in a if statement that didn't get flagged before the change in the latest release. Below is the full output:

Debug Trace
For /Users/bkuhlmann/Engineering/OSS/git-lint: configuration from /Users/bkuhlmann/Engineering/OSS/git-lint/.rubocop.yml
configuration from /Users/bkuhlmann/Engineering/OSS/git-lint/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-ruby-yml
Default configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-1.22.0/config/default.yml
configuration from /Users/bkuhlmann/Engineering/OSS/git-lint/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rake-yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-rake-0.6.0/config/default.yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-rake-0.6.0/config/default.yml
configuration from /Users/bkuhlmann/Engineering/OSS/git-lint/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-performance-yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-performance-1.11.5/config/default.yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-performance-1.11.5/config/default.yml
configuration from /Users/bkuhlmann/Engineering/OSS/git-lint/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rspec-yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-rspec-2.5.0/config/default.yml
configuration from /Users/bkuhlmann/.cache/frum/versions/3.0.2/lib/ruby/gems/3.0.0/gems/rubocop-rspec-2.5.0/config/default.yml
Running parallel inspection
For /Users/bkuhlmann/Engineering/Misc: configuration from /Users/bkuhlmann/.config/rubocop/config.yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-ruby-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rake-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-performance-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rspec-yml
Loading cache from /Users/bkuhlmann/.cache/rubocop_cache/7cd34d310cda33d35ab370b487ae14bb76d5a73e/132c4e53bc39cc09f7d3f2461c2f48ebce8751d3/ac0019aa6070aba42163cf1bca85c5ed3bf19db3
Inspecting 1 file
Scanning /Users/bkuhlmann/Engineering/Misc/snippet.rb
For /Users/bkuhlmann/Engineering/Misc: configuration from /Users/bkuhlmann/.config/rubocop/config.yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-ruby-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rake-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-performance-yml
configuration from /Users/bkuhlmann/.config/rubocop/.rubocop-https---raw-githubusercontent-com-bkuhlmann-code-quality-main-configurations-rubocop-rspec-yml
Loading cache from /Users/bkuhlmann/.cache/rubocop_cache/7cd34d310cda33d35ab370b487ae14bb76d5a73e/132c4e53bc39cc09f7d3f2461c2f48ebce8751d3/ac0019aa6070aba42163cf1bca85c5ed3bf19db3
W

Offenses:

/Users/bkuhlmann/Engineering/Misc/snippet.rb:21:1: C: [Correctable] Style/CaseLikeIf: Convert if-elsif to case-when. (https://rubystyle.guide#case-vs-if-else)
if number == 1 then puts "One" ...
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
/Users/bkuhlmann/Engineering/Misc/snippet.rb:23:6: W: [Correctable] Lint/ElseLayout: Odd else layout detected. Did you mean to use elsif?
else "Unknown."
     ^^^^^^^^^^

1 file inspected, 2 offenses detected, 2 offenses auto-correctable
Finished in 0.22139099997002631 seconds

You can ignore the Style/CaseLikeIf issue as that's legit because I'm using a case statement for comparison purposes below.

Steps to reproduce the problem

Throw the following in snippet.rb and run Rubocop against it:

number = 1

case number
  when 1 then puts "One"
  when 2 then puts "Two"
  else "Unknown"
end

if number == 1 then puts "One"
elsif number == 2 then puts "Two"
else "Unknown"
end

The above code is silly but notice how the else in the case and if statements used to be allowed. However, with the latest version, you now have to write the if statement like this to fix the Lint/ElseLayout issue:

if number == 1 then puts "One"
elsif number == 2 then puts "Two"
else
  "Unknown"
end

This seems wrong to me because it's not consisent with case statements but, more importantly, if you have simple statements above the else all on one line, why can't else be a one liner as well in order to maintain symmetry?

RuboCop version

rubocop -V

1.22.0 (using Parser 3.0.2.0, rubocop-ast 1.12.0, running on ruby 3.0.2 arm64-darwin20.5.0)
  - rubocop-performance 1.11.5
  - rubocop-rake 0.6.0
  - rubocop-rspec 2.5.0

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions