Class: RuboCop::Cop::Obsession::NoBreakOrNext

Inherits:
Base
  • Object
show all
Defined in:
lib/rubocop/cop/obsession/no_break_or_next.rb

Overview

This cop checks for ‘next` (and sometimes `break`) in loops.

  • For big loops, ‘next` or `break` indicates that the loop body has

significant logic, which means it should be moved into its own method, and you can convert the ‘next` or `break` into `return` and the like.

  • For small loops, you can just use normal conditions instead of ‘next`.

‘break` is allowed.

Note: Sometimes loops can also be rethought, like transforming a ‘loop` + `break` into a `while`.

Examples:


# bad
github_teams.each do |github_team|
  next if github_team['size'] == 0
  team = @company.teams.find_or_initialize_by(github_team['id'])

  team.update!(
    name: github_team['name'],
    description: github_team['description'],
    owner: @company,
  )
end

# good
github_teams.each do |github_team| { |github_team| upsert_team(github_team) }

def upsert_team(github_team)
  return if github_team['size'] == 0
  team = @company.teams.find_or_initialize_by(github_team['id'])

  team.update!(
    name: github_team['name'],
    description: github_team['description'],
    owner: @company,
  )
end

# bad
def highlight
  blog_posts.each do |blog_post|
    next if !blog_post.published?

    self.highlighted = true
  end
end

# good
def highlight
  blog_posts.each do |blog_post|
    if blog_post.published?
      self.highlighted = true
    end
  end
end

Constant Summary collapse

BIG_LOOP_MSG =
'Avoid `break`/`next` in big loop, decompose into private method or rethink loop.'
NO_NEXT_MSG =
'Avoid `next` in loop, use conditions or rethink loop.'
BIG_LOOP_MIN_LINES =
7

Instance Method Summary collapse

Instance Method Details

#on_block(node) ⇒ Object



76
77
78
79
80
81
82
83
84
# File 'lib/rubocop/cop/obsession/no_break_or_next.rb', line 76

def on_block(node)
  return if !contains_break_or_next?(node)

  if big_loop?(node)
    add_offense(node, message: BIG_LOOP_MSG)
  elsif contains_next?(node)
    add_offense(node, message: NO_NEXT_MSG)
  end
end