0

我在进行集成测试时遇到了麻烦,因为用户在我的 rails 应用程序中登录,通过。

我正在使用 Rspec 和 capybara,以及设计用户身份验证

这是我的代码:

请求/身份验证_spec.rb

describe 'log in' do
  before { visit root_path }
  subject { page }

  describe 'should be able to log in' do
    before do
      user = FactoryGirl.create(:user)
      fill_in :user_email, with: user.email
      fill_in :user_password, with: user.password
      click_on 'Log in'
    end
    it { should have_link 'Log out' }
  end
end

工厂/user_factory.rb

FactoryGirl.define do
  factory :user do
    sequence( :first_name )  { |n| "FirstName#{n}" }
    sequence( :last_name )  { |n| "LastName#{n}" }
    sequence( :email ) { |n| "foo#{n}@example.com" }
    password              'foobar'
    password_confirmation 'foobar'
    created_at            Time.now
    updated_at            Time.now
  end
end

_login_form.html.erb,此表单呈现在应用程序布局标题中。

<%= form_for(resource, as: resource_name, url: session_path(resource_name), html: { id: 'login-mini-form' }) do |f| %>
  <%= f.email_field :email,       placeholder: 'Your email' %>
  <%= f.password_field :password, placeholder: '******' %>
  <%= f.submit "Log in", id: 'login-button' %>

  <%- if devise_mapping.rememberable? -%>
    <%= f.check_box :remember_me %> <%= f.label :remember_me %>
  <%- end -%>

<% end %>

在布局中,我有类似的东西:

if user_signed_in?
  render 'devise/menu/logout_button'
else
  render 'devise/menu/login_form'
end

测试给了我

1) User should be able to log in with valid credentials 
     Failure/Error: it { should have_link 'Log out' }
       expected link "Log out" to return something
     # ./spec/requests/authentications_spec.rb:117:in `block (6 levels) in <top (required)>'

Finished in 0.71406 seconds
8 examples, 2 failures, 2 pending

我不明白为什么我的测试没有通过。有任何想法吗 ?

非常感谢 !

编辑:我得到相同的行为测试注册:expect { click_button register_button }.to change(User, :count).by 1,测试返回:

Failure/Error: expect { click_button register_button }.to change(User, :count).by 1
       count should have been changed by 1, but was changed by 0
4

2 回答 2

1

所以,我发现什么不起作用:

describe 'log in' do
  before { visit root_path }
  subject { page }

  describe 'should be able to log in' do
    before do
      user = FactoryGirl.create(:user)
      fill_in :user_email, with: user.email
      fill_in :user_password, with: user.password
      click_on 'Log in'
    end
    it { should have_link 'Log out' }
  end

正确的代码实际上是:

describe 'log in' do
  before { visit root_path }
    subject { page }

    describe 'should be able to log in' do
      before do
        user = FactoryGirl.create(:user)
        fill_in 'user_email', with: user.email
        fill_in 'user_password', with: user.password
        click_on 'Log in'
      end
      it { should have_link 'Log out' }
    end
  end
end

似乎 Capybara fill_in 方法不将符号作为 ids 的参数,而仅将字符串作为参数。傻我。

于 2012-07-04T11:07:29.010 回答
0

您没有提供您期望的主题,所以看起来 RSpec 正在使用最后一个表达式的结果。最后一个表达式是 your click_button,它不返回任何内容。你不能should什么都不叫。

要解决这个问题,您只需要指定页面应该有链接。我使用 Capybara 和 Selenium-Webdriver,所以对我来说它看起来像page.should have_link.... 我的 RSpec-fu 不够强大,无法知道您是否也应该使用page,或者替代response,session或其他东西。

于 2012-07-03T23:57:18.840 回答