Upload
tim-moore
View
4.738
Download
4
Embed Size (px)
DESCRIPTION
Capybaras are the largest rodents in the world. They are related to guinea pigs, but are the size of a big dog or small pig. They live in South America, and they're pretty damn cute. Capybara is also the name of a Ruby gem written by Jonas Nicklas. It helps you write integration tests for web apps by pretending to be a user with a web browser. It takes a black box approach to testing, letting you go to URLs, click links and buttons, fill in forms, and check that the rendered page contains what you think it should have in it. This talk is about Embracing Capybara: how to understand Capybara, train it to do new tricks, and discipline it when it misbehaves.
Citation preview
Embracing Capybara
Who Has Used Capybara?
Who Has Been Bitten By Capybara?
TimMoore
tmoore
What’s a Capybara?
World’s Largest Rodent!
“Makes it easy to simulate how a user interacts with your application”
http://git.io/capybara
Capybara Anatomy
Browsing DSL
Matchers/Selectors
Browser Engines
visit '/sessions/new' within("#session") do fill_in 'Login', with: '[email protected]' fill_in 'Password', with: 'password' end click_link 'Sign in' expect(page).to have_content 'Success'
Understanding Capybara
Capybara is Patientvisit '/sessions/new'
within("#session") do fill_in 'Login', with: '[email protected]'
fill_in 'Password', with: 'password'end
click_link 'Sign in'
expect(page). to have_content 'Success'
Waits for page to load
Capybara is Patientvisit '/sessions/new'
within("#session") do fill_in 'Login', with: '[email protected]'
fill_in 'Password', with: 'password'end
click_link 'Sign in'
Capybara.using_wait_time(60) do expect(page). to have_content 'Success'end
Waits for page to load
Capybara is Patientvisit '/sessions/new'
within("#session") do fill_in 'Login', with: '[email protected]'
fill_in 'Password', with: 'password'end
click_link 'Sign in'
expect(page). to have_content 'Success', wait: 60
Waits for page to load
Methods that Wait• find(selector), find_field, find_link, etc.
• within(selector) (scoping)
• has_selector?/has_no_selector? & assertions
• form & link actions
• click_link/button
• fill_in
• check/uncheck, select, choose, etc.
Methods that Don’t• visit(path)
• current_path
• all(selector)
• first(selector) (counter-intuitively)
• execute_script/evaluate_script
• simple accessors: text, value, title, etc.
Don’t Do This
click_link('Search') expect(all('.search-result').count). to eq 2
Returns 0Does not wait
Good
click_link('Search') expect(page). to have_css '.search-result', count: 2
Don’t Do This
click_button('Save') expect(find('.dirty-warning').text). not_to contain('Unsaved changes')
Does not wait
Good
click_button('Save') expect(find('.dirty-warning')). to have_no_text('Unsaved changes')
Also Good
click_button('Save') expect(find('.dirty-warning')). not_to have_text('Unsaved changes')
Training Capybara
Don’t Do ThisScenario: Searching for cats Given I am on "/search" When I fill in "input.search_text" with "cats" And I press "Search" Then I should see "grumpy cat" within "div.search-results"
Don’t Do ThisScenario: Searching for cats Given I am on "/search" When I fill in "input.search_text" with "cats" And I press "Search" Then I should see "grumpy cat" within "div.search-results"
“A step description should never contain regexen, CSS or XPath selectors”
“web_steps.rb is a terrible, terrible idea” - Boring scenarios - Brittle scenarios - Where is my workflow?
BetterScenario: Searching for cats Given I am on the search page When I fill in "Search" with "cats" And I press "Search" Then I should see "grumpy cat" within the search results
BestScenario: Searching for cats When I search for "cats" Then I should see "grumpy cat" within the search results
Don’t Do ThisWhen /^I search for "([^"]*)"$/ do |search_text| visit "/search" fill_in "input.search_text", with: search_text click_button "Search" end
BetterWhen /^I search for "([^"]*)"$/ do |search_text| search_page = my_app.search_page search_page.search_input. fill_in search_text search_page.search_button.click end
Betterclass MyAppTester def initialize @session = Capybara::Session.new(:selenium) end !
def search_page MyAppTester::SearchPage.new(@session) end end
Betterclass MyAppTester::SearchPage def initialize(session) session.visit "/search" @session = session end def search_input @session.find "input.search_text" end def search_button @session.find "button.search" end end
BetterWhen /^I search for "([^"]*)"$/ do |search_text| search_page = my_app.search_page search_page.search_input. fill_in search_text search_page.search_button.click end
BestWhen /^I search for "([^"]*)"$/ do |search_text| my_app.search_for search_text end
Don’t Do Thisfind(:css, "div.main div.sidebar div.search div.advanced div.actions button.submit").click
Failure/Error: find(:css, "div.main div.sidebar div.search div.advanced div.actions button.submit").click Capybara::ElementNotFound: Unable to find css "div.main div.sidebar div.search div.advanced div.actions button.submit"
Disciplining Capybara
Setting Breakpoints
When /^I debug$/ do debugger end
Taking ScreenshotsAfter do |scenario| filename = scenario.name.gsub(/\W/, '_') page.save_screenshot( "target/reports/#{filename}.png") end !
http://git.io/capybarascreenshot
Firefox•focusmanager.testmode = true
• Update selenium-webdriver gem
• Disable auto-update in CI
• Beware platform differences
• http://git.io/capybarafirebug
Getting Help
• http://groups.google.com/group/ruby-capybara
• Freenode (IRC): #capybara
• Stack Overflow
Summary• Understand Capybara synchronisation
• Be explicit with Capybara
• Use Page Objects for readable, flexible tests
• Keep selectors simple
• If you get bitten, seek help!
Fix Flaky Tests
Thanks! Any Questions?