capybara-compose icon indicating copy to clipboard operation
capybara-compose copied to clipboard

✅ Easily write fluent integration tests with Capybara in Ruby

Capybara Test Helpers

Build Status Maintainability Test Coverage Gem Version License

Capybara Test Helpers allows you to easily encapsulate logic in your integration tests.

Write tests that everyone can understand, and leverage your Ruby skills to keep them easy to read and easy to change.

Features ⚡️

Locator Aliases work with every Capybara method, allowing you to encapsulate CSS selectors and labels, and avoid coupling tests with the implementation.

The entire Capybara DSL is available, and element results are wrapped automatically so that you can chain your own assertions and actions fluently.

A powerful syntax for assertions and convenient primitives for synchronization enable you to write async-aware expectations: say goodbye to flaky tests.

Documentation 📖

Visit the documentation website to check out the guides, searchable API reference, and examples.

Installation 💿

Add this line to your application's Gemfile:

gem 'capybara_test_helpers'

To use with RSpec, add the following to your spec_helper.rb:

require 'capybara_test_helpers/rspec'

To use with Cucumber, add the following to your support/env.rb:

require 'capybara_test_helpers/cucumber'

Additional installation instructions are available in the documentation website.

Quick Tour 🛣

Let's say we have a list of cities, and we want to test the Edit functionality using Capybara.

scenario 'editing a city' do

  within('.cities') {
    find(:table_row, { 'Name' => 'NYC' }).click_on('Edit')
  fill_in 'Name', with: 'New York City'
  click_on('Update City')

  within('.cities') {
    expect(page).not_to have_selector(:table_row, { 'Name' => 'NYC' })
    expect(page).to have_selector(:table_row, { 'Name' => 'New York City' })

Even though it gets the job done, it takes a while to understand what the test is trying to do.

Without discipline these tests can become hard to manage and require frequent updating.

Using Test Helpers

We can avoid the duplication and keep the focus on the test instead of its implementation by using test helpers.

scenario 'editing a city', test_helpers: [:cities] do

  cities.edit('NYC', with: { name: 'New York City' })

  cities.should_now.have_city('New York City')

Learn more about it in the documentation website.

Special Thanks 🙏

This library wouldn't be the same without early validation from my colleagues, and numerous improvements and bugfixes they contributed to it. Thanks for the support 😃

  • capybara: Excellent library to write integration tests in Ruby.


The gem is available as open source under the terms of the MIT License.