ruby-on-rails - Rails + Cucumber/Capybara : How to set/retrieve cookies in tests?

标签 ruby-on-rails cookies capybara

我正在实现一个惰性登录功能。我的 cucumber 功能应该描述它:

    Feature: User log in

        Scenario: Lazy login
            Given I didn't log out the last time I was on the site
            When I go to the homepage
            Then I should automatically be logged in 

这些是我的步骤定义:
Given(/^I didn't log out the last time I was on the site$/) do
  user = FactoryGirl.create(:user)
  visit new_user_session_path
  fill_in('user[email]', with: user.email)
  fill_in('user[password]', with: 'test123')
  click_button('Sign in')

  Capybara.reset_sessions!
end

When(/^I go to the homepage$/) do
  visit root_path
end

Then(/^I should automatically be logged in$/) do #<-- Fails here
  page.should have_content("Logout")
end

这是用户登录时发生的情况:cookies.signed[:auth_token]设置。这将由我的 ApplicationController 中的前置过滤器使用,以便打开新浏览器的用户将自动登录:
class SessionsController < Devise::SessionsController

def create
  super
  if user_signed_in?
    puts 'yesssssss'
    session[:user_id] = current_user.id  
    current_user.remember_me! if current_user.remember_token.blank?
    cookies.signed[:auth_token] = {
      :value => current_user.remember_token,
      :domain => "mysite.com",
      :secure => !(Rails.env.test? || Rails.env.development?)
      }
    puts "current_user.remember_token = #{current_user.remember_token}"
    puts 'cookies:'
    puts cookies.signed[:auth_token]
  end
end

结尾

这是我的 ApplicationController 中的前置过滤器:
def sign_in_through_cookie
  logger.info "logging in by cookie"
  puts "logging in by cookie"
  puts cookies.signed[:auth_token] #<-- PROBLEM: this returns nil.
  return true if !current_user.nil?
  if !cookies[:auth_token].nil? && cookies[:auth_token] != ''
    user = User.find_by_remember_token(cookies.signed[:auth_token])
    return false if user.blank?
    sign_in(user)
    puts 'success'
    return true
  else
    return false
  end
end

所以问题是在我的 cucumber 功能的最后一步,cookies.signed[:auth_token]返回零。我猜这只是 capybara 的事情。那么我实际上是否必须在测试中设置一个 cookie 而不是在我的 Controller 中使用一个?

最佳答案

所以最终我在尝试了很多不同的事情后想通了。

Given(/^I didn't log out the last time I was on the site$/) do
  user = FactoryGirl.create(:user)
  visit new_user_session_path
  fill_in('user[email]', with: user.email)
  fill_in('user[password]', with: 'test123')
  click_button('Sign in')

  Capybara.current_session.driver.request.cookies.[]('auth_token').should_not be_nil
  auth_token_value = Capybara.current_session.driver.request.cookies.[]('auth_token')
  Capybara.reset_sessions!
  page.driver.browser.set_cookie("auth_token=#{auth_token_value}")
end

When(/^I go to the homepage$/) do
  visit root_path
end

Then(/^I should automatically be logged in$/) do
  page.should have_content("Logout")
end

更新:

这是我在使用 Selenium 进行某些测试时使用的内容:
if Capybara.current_session.driver.class == Capybara::Selenium::Driver
  auth_token = page.driver.browser.manage.cookie_named('auth_token')[:value]
  page.driver.browser.manage.delete_all_cookies
  page.driver.browser.manage.add_cookie(:name => "auth_token", :value => auth_token)
else
  puts "cookies = #{Capybara.current_session.driver.request.cookies}"
  Capybara.current_session.driver.request.cookies.[]('auth_token').should_not be_nil
  auth_token_value = Capybara.current_session.driver.request.cookies.[]('auth_token')
  Capybara.reset_sessions!
  page.driver.browser.set_cookie("auth_token=#{auth_token_value}")
end

关于ruby-on-rails - Rails + Cucumber/Capybara : How to set/retrieve cookies in tests?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19325960/

相关文章:

javascript - 如何为表行结果的每个按钮添加事件监听器?

ruby-on-rails - 在 ruby​​ 中评估 SCSS (SASS) 模板(Rails 元素)

ruby-on-rails - Rails 延迟作业和库类

ruby-on-rails - 使用 form_tag 时传递错误消息?

javascript - 我无法使用 perl 脚本获取网站内容

javascript - 如何使用 capybara 从 ruby​​ 调用异步 javascript 函数?

angularjs - 在 Spring Security 或 Angular 中注销时清除 Cookie

cookies - 我们还需要担心用户关闭 cookie 吗?

ruby - 如何运行独立的 Capybara 测试?

button - capybara - 单击没有 id 的按钮