Is it possible to take a screenshot of the whole page with Selenium/Capybara?

You could also do something like this:

After do |scenario|
  take_screenshot(@browser, scenario)
end

def take_screenshot(browser, scenario)
  if scenario.failed?
    scenario_name = scenario.name.gsub /[^\w\-]/, ' '
    time = Time.now.strftime("%Y-%m-%d %H%M")
    screenshot_path = './failed_png/' + time + ' - ' + scenario_name + '.png'
  else
    scenario_name = scenario.name.gsub /[^\w\-]/, ' '
    time = Time.now.strftime("%Y-%m-%d %H%M")
    screenshot_path = './success_png/' + time + ' - ' + scenario_name + '.png'
  end
  browser.save_screenshot(screenshot_path)
end

If you make a failed_png and success_png folder, this code will take a screenshot for each success and failure, and put it in the respective folders with the timestamp on it. This code goes in your env.rb file, and makes it so you do not have to use any helpers or add any extra code to your step defs.


In case anyone washed up this shore looking for how to do this with Poltergeist you just need to pass the full argument:

page.save_screenshot('screen.png', full: true) # If providing a custom file name.
page.save_screenshot(full: true)               # Capybara sets a name based on timestamp.
page.save_and_open_screenshot('screen.png', full: true) # Same as save_screenshot.
page.save_and_open_screenshot(full: true)               # Same as save_screenshot.

Docs.

Hope it helps!


I tried a lot of things to get full height working with Capybara/Selenium.

Only one thing I tried seemed to work, and it was using headless_chrome. Bear in mind that I use a loop to take screenshots at different widths:

  def screenshot
    driver = Capybara.current_session.driver
    window = Capybara.current_session.driver.browser.manage.window
    widths = [320, 1380] #leave normal w as last
    widths.each do |w|
      window.resize_to(w, 900)
      total_width = driver.execute_script("return document.body.offsetWidth")
      total_height = driver.execute_script("return document.body.scrollHeight")
      window.resize_to(total_width, total_height)
      save_screenshot
    end
  end

I resize it twice to get the height info.

rails_helper.rb:

Capybara.register_driver :headless_chrome do |app|
  capabilities = Selenium::WebDriver::Remote::Capabilities.chrome(
    chromeOptions: { 
      "args" => %w{ 
        headless 
        disable-gpu
        --disable-notifications
      } 
    }
  )
  Capybara::Selenium::Driver.new app,
    browser: :chrome,
    desired_capabilities: capabilities
end

Capybara.javascript_driver     = :headless_chrome
Capybara.current_driver        = :headless_chrome

Turns out I've been using the take_screenshot method that was provided by the headless gem, when I could have just used the page.save_screenshot() method, which does exactly what I need. Thank you, Andrey.