Skip to content

Style/SafeNavigation reports on complex nil checks that should pass #14420

@martinemde

Description

@martinemde

Expected behavior

The following code is flagged as a Style/SafeNavigation violation.

end_time = end_date.nil? ? nil : end_date.in_time_zone(timezone) + 1.day

The shape of the code actually matches one of the exceptions listed in the documentation:

foo ? foo * 42 : nil      # Ignored `foo&.*(42)` due to unclear readability benefit.

I think the correct fix is to ignore any safe navigation where there is arithmetic or other ignored methods (like []) anywhere in the non-nil side of the conditional.

Actual behavior

Arithmetic calls are excepted in the docs due to readability, but because there is a method call before the arithmetic but inside the conditional, rubocop incorrectly fixes to non-functional code.

end_time = end_date&.in_time_zone(timezone) + 1.day

This seems to have started around 1.79, since we're only getting these violations now, whereas they weren't triggering before, though I'm not certain this is the exact version where it changed.

Steps to reproduce the problem

Save the following code:

end_time = end_date.nil? ? nil : end_date.in_time_zone(timezone) + 1.day

See that it violates Style/SafeNavigation. It should not.

Try auto-correct, see that it produces code that will error when nil receives +.

RuboCop version

$ bundle exec rubocop -V
1.79.1 (using Parser 3.3.8.0, Prism 1.4.0, rubocop-ast 1.46.0, analyzing as Ruby 3.4, running on ruby 3.4.5) +server [arm64-darwin24]
  - rubocop-rspec 3.6.0
  - rubocop-performance 1.25.0
  - rubocop-rake 0.7.1
  - rubocop-capybara 2.22.1
  - rubocop-factory_bot 2.27.1
  - rubocop-graphql 1.5.6
  - rubocop-performance 1.25.0
  - rubocop-rake 0.7.1
  - rubocop-rspec 3.6.0
  - rubocop-rspec_rails 2.31.0
  - rubocop-sorbet 0.10.5
  - rubocop-rails 2.32.0

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions