Capybara: Ruby Acceptance Testing for Web Apps
Capybara is a Ruby library for acceptance tests: visit pages, fill forms, click and assert, with RackTest, Selenium or Cuprite drivers and built-in waits.
What is Capybara?
Capybara is a Ruby library for acceptance tests of web applications. It gives you a DSL to visit pages, fill in forms, click links and assert on what is rendered, and it runs through either a simple in-process driver or a real browser. It is not a test runner: you use it inside RSpec, Minitest or Cucumber. Rails system tests are built on it.
How Capybara works
Your test describes what a user does, and Capybara hands each step to a driver. The default driver, RackTest, is pure Ruby, needs no server and has no JavaScript support, so it is fast but cannot run scripts. For pages that depend on JavaScript you switch to a browser driver. Capybara.javascript_driver defaults to :selenium, and a test uses it when tagged js: true in RSpec or @javascript in Cucumber. Cuprite is a separate gem that drives Chrome through the Chrome DevTools Protocol and needs no Selenium or ChromeDriver.
Example
require 'rails_helper'
RSpec.describe 'Signup', type: :system do
it 'creates an account' do
visit '/signup'
fill_in 'Email', with: 'alice@example.com'
fill_in 'Password', with: 'secret123'
click_button 'Create account'
expect(page).to have_content 'Welcome, alice'
end
endThere is no sleep in it. Finders and matchers such as have_content retry until they pass or the wait time runs out, and return at once on success. The default Capybara.default_max_wait_time is 2 seconds; raise it with Capybara.default_max_wait_time = 5 if a page is genuinely slow. Rails system tests default to Selenium with Chrome and let you pick another driver with driven_by.
Common mistakes
- Fixed sleeps. They slow the suite and still fail on a slow run. Use a waiting matcher instead of
sleep. - Negative checks that do not wait. Prefer
expect(page).to have_no_content(...)over!page.has_content?(...), which gives up at the first look. - Expecting JavaScript from RackTest. If a click does nothing, check that the test runs on a JavaScript driver.
- Brittle selectors. Prefer labels and visible text over long CSS paths that break on every redesign.
- Flaky data setup. Races between the browser and the app server are a main source of flaky tests.
Capybara in a test strategy
Capybara checks that a feature works for one user in a browser. It is slow compared with unit tests, so keep it for the key journeys: signup, checkout, login. It is a good fit for regression testing of those flows, and it works with the rendered DOM rather than your internals. If you work outside Ruby, the same idea is covered for Playwright in our Playwright tutorial.
What it does not tell you is how the app behaves with many users at once. For that, run a load test against the same journeys.
FAQ about Capybara
Is Capybara a test framework?
No. It is a library for driving a web app, used inside RSpec, Minitest or Cucumber, which provide the test structure and reporting.
Which drivers does Capybara support?
RackTest is the default and has no JavaScript. Selenium drives real browsers. Cuprite drives Chrome through the DevTools Protocol, and other drivers such as WebKit are available as external gems.
How long does Capybara wait?
By default 2 seconds, set with Capybara.default_max_wait_time. Finders and matchers retry within that time and return immediately once they succeed.
Do I need Selenium to use Capybara?
No. RackTest needs no browser, and Cuprite uses Chrome directly. Selenium is the default JavaScript driver and what Rails system tests use unless you change it.
Does Capybara work with Rails?
Yes. Rails system tests are built on Capybara, and you choose the browser driver with driven_by in the system test case.
Related terms
Related LoadFocus Tools
Put this concept into practice with LoadFocus, the same platform that powers everything you just read about.