class RuboCop::Cop::RSpec::RepeatedIncludeExample

Check for repeated include of shared examples.

@example

# bad
describe 'foo' do
  include_examples 'cool stuff'
  include_examples 'cool stuff'
end

# bad
describe 'foo' do
  it_behaves_like 'a cool', 'thing'
  it_behaves_like 'a cool', 'thing'
end

# bad
context 'foo' do
  it_should_behave_like 'a duck'
  it_should_behave_like 'a duck'
end

# good
describe 'foo' do
  include_examples 'cool stuff'
end

describe 'bar' do
  include_examples 'cool stuff'
end

# good
describe 'foo' do
  it_behaves_like 'a cool', 'thing'
  it_behaves_like 'a cool', 'person'
end

# good
context 'foo' do
  it_should_behave_like 'a duck'
  it_should_behave_like 'a goose'
end

Constants

MSG

Public Instance Methods

on_begin(node) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 67
def on_begin(node)
  return unless several_include_examples?(node)

  repeated_include_examples(node).each do |item, repeats|
    add_offense(item, message: message(item, repeats))
  end
end

Private Instance Methods

add_repeated_lines(items) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 92
def add_repeated_lines(items)
  repeated_lines = items.map(&:first_line)
  items.map { |item| [item, repeated_lines - [item.first_line]] }
end
literal_include_examples?(node) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 87
def literal_include_examples?(node)
  include_examples?(node) &&
    node.arguments.all?(&:recursive_literal_or_const?)
end
message(item, repeats) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 101
def message(item, repeats)
  format(MSG, name: shared_examples_name(item).source, repeat: repeats)
end
repeated_include_examples(node) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 77
def repeated_include_examples(node)
  node
    .children
    .select { |child| literal_include_examples?(child) }
    .group_by { |child| signature_keys(child) }
    .values
    .reject(&:one?)
    .flat_map { |items| add_repeated_lines(items) }
end
signature_keys(item) click to toggle source
# File lib/rubocop/cop/rspec/repeated_include_example.rb, line 97
def signature_keys(item)
  item.arguments
end