RSpec examples can get quite long, especially in feature specs. This makes them hard to read & understand. Also, when executing them, it may take seconds to see any progress.
To improve this, I have successfully been using a little "step" helper in my tests. It marks semantic sections, structuring an example while improving documentation. When the test runs, each step prints its message (or a dot, depending on your formatter).
# spec/support/step_helper.rb
module StepHelper
# Use this helper to label groups of related actions in long specs.
# This helps understanding a spec, as well as tracking progress during execution.
#
# Example:
# it 'offers a login' do
# # Test setup
#
# STEP 'Attempt login with wrong credentials'
# # ...
#
# STEP 'Successful login'
# # ...
# end
def STEP(label)
formatters = RSpec.configuration.formatters.map(&:class)
example = RSpec.current_example
hierarchy = example.example_group.parent_groups
indent = ' ' * hierarchy.count
if formatters.include? RSpec::Core::Formatters::DocumentationFormatter
puts "#{indent}⮦ #{label}"
elsif formatters.include? RSpec::Core::Formatters::ProgressFormatter
print '.'
else
raise "Unexpected RSpec formatters: #{formatters.map(&:name)}"
end
end
end
RSpec.configure do |config|
config.include StepHelper
end
Usage example
scenario 'The list of advisories is paginated' do
elements_per_page(DepReporter::Advisory, 2)
create(:npm_advisory, title: 'oldest', created_at: '2019-05-01')
create(:npm_advisory, title: 'advisory', created_at: '2019-06-01')
create(:npm_advisory, title: 'latest', created_at: '2019-07-01')
STEP 'visit the first page of advisories'
visit advisories_path
expect(page).to have_content('latest')
.and have_content('advisory')
.and have_no_content('oldest')
STEP 'navigate to the second page'
click_link '2'
expect(page).to have_content('oldest')
.and have_no_content('latest')
.and have_no_content('advisory')
end
Posted by Dominik Schöler to makandra dev (2025-08-22 13:56)