【问题标题】:Rails Rspec error - undefined method `visit'Rails Rspec 错误 - 未定义的方法“访问”
【发布时间】:2013-04-21 23:26:10
【问题描述】:

所以我是 TDD 新手,我在测试中抛出了一些 Rspec 错误...基本上在运行 bundle exec rspec spec 之后,我的一些规范出现undefined method 'visit' 错误。任何有关如何使这些测试通过的帮助将不胜感激:谢谢。

Failures:

1) User pages profile page 
 Failure/Error: before { visit user_path(user) }
 NoMethodError:
   undefined method `visit' for # <RSpec::Core::ExampleGroup::Nested_2::Nested_1:0x007ffda8049540>
 # ./spec/requests/user_pages_spec.rb:9:in `block (3 levels) in <top (required)>'

2) User pages profile page 
 Failure/Error: before { visit user_path(user) }
 NoMethodError:
   undefined method `visit' for #<RSpec::Core::ExampleGroup::Nested_2::Nested_1:0x007ffda4f3ac38>
 # ./spec/requests/user_pages_spec.rb:9:in `block (3 levels) in <top (required)>'

3) User pages signup page 
 Failure/Error: before { visit signup_path }
 NoMethodError:
   undefined method `visit' for #<RSpec::Core::ExampleGroup::Nested_2::Nested_2:0x007ffda8262e58>
 # ./spec/requests/user_pages_spec.rb:16:in `block (3 levels) in <top (required)>'

4) User pages signup page 
 Failure/Error: before { visit signup_path }
 NoMethodError:
   undefined method `visit' for #<RSpec::Core::ExampleGroup::Nested_2::Nested_2:0x007ffda82663c8>
 # ./spec/requests/user_pages_spec.rb:16:in `block (3 levels) in <top (required)>'

Finished in 9.08 seconds
24 examples, 4 failures

Failed examples:

rspec ./spec/requests/user_pages_spec.rb:11 # User pages profile page 
rspec ./spec/requests/user_pages_spec.rb:12 # User pages profile page 
rspec ./spec/requests/user_pages_spec.rb:18 # User pages signup page 
rspec ./spec/requests/user_pages_spec.rb:19 # User pages signup page 

我的规范/请求/user_pages_spec.rb

require 'spec_helper'

describe "User pages" do

  subject { page }

  describe "profile page" do
    let(:user) { FactoryGirl.create(:user) } # Code to make a user variable
    before { visit user_path(user) }

    it { should have_selector('h1',    text: user.name) }
    it { should have_selector('title', text: user.name) }
  end

  describe "signup page" do
    before { visit signup_path }

    it { should have_selector('h1',    text: 'Sign up') }
    it { should have_selector('title', text: 'Sign up') }
  end
end

还有我的 spec/models/user_spec.rb

require 'spec_helper'

describe User do

before do
  @user = User.new(name: "Example User", email: "user@example.com",
                  password: "foobar", password_confirmation: "foobar")
end

subject { @user }

it { should respond_to(:name) }
it { should respond_to(:email) }
it { should respond_to(:password_digest) }
it { should respond_to(:password) }
it { should respond_to(:password_confirmation) }
it { should respond_to(:authenticate) }

it { should be_valid }

describe "when name is not present" do
  before { @user.name = " " }
  it { should_not be_valid }
end

describe "when email is not present" do
  before { @user.email = " " }
  it { should_not be_valid }
end

describe "when name is too long" do
  before { @user.name = "a" * 51 }
  it { should_not be_valid }
end

describe "when email format is invalid" do
  it "should be invalid" do
    addresses = %w[user@foo,com user_at_foo.org example.user@foo.
                   foo@bar_baz.com foo@bar+baz.com]
    addresses.each do |invalid_address|
      @user.email = invalid_address
      @user.should_not be_valid
    end      
  end
end

describe "when email format is valid" do
  it "should be valid" do
    addresses = %w[user@foo.COM A_US-ER@f.b.org frst.lst@foo.jp a+b@baz.cn]
    addresses.each do |valid_address|
      @user.email = valid_address
      @user.should be_valid
    end      
  end
end

describe "when email address is already taken" do
  before do
    user_with_same_email = @user.dup
    user_with_same_email.email = @user.email.upcase
    user_with_same_email.save
  end
  it { should_not be_valid }
end

describe "when password is not present" do
  before { @user.password = @user.password_confirmation = " " }
  it { should_not be_valid }
end

describe "with a password that's too short" do
  before { @user.password = @user.password_confirmation = "a" * 5 }
  it { should be_invalid }
end

describe "return value of authenticate method" do
  before { @user.save }
  let(:found_user) { User.find_by_email(@user.email) }

  describe "with valid password" do
    it { should == found_user.authenticate(@user.password) }
  end

  describe "with invalid password" do
    let(:user_for_invalid_password) { found_user.authenticate("invalid") }

    it { should_not == user_for_invalid_password }
    specify { user_for_invalid_password.should be_false }
  end
end 

describe "when password doesn't match confirmation" do
  before { @user.password_confirmation = "mismatch" }
  it { should_not be_valid }
end

describe "when password confirmation is nil" do
  before { @user.password_confirmation = nil }
  it { should_not be_valid }
end

end

最后是我的观点/用户/new.html.erb

<% provide(:title, 'Sign up') %>
<h1>Sign up</h1>
<p>Find me in app/views/users/new.html.erb</p>

和视图/用户/show.html.erb

<% provide(:title, @user.name) %>
<h1><%= @user.name %></h1>

& 我已经添加了我的用户控制器

class UsersController < ApplicationController
  def new
  end

  def show
   @user = User.find(params[:id])
  end
end

在按照比利的解决方案修复后,现在也出现了这个新错误

Failures:

1) User pages signup page 
 Failure/Error: it { should have_selector('title', text: 'Sign up') }
 Capybara::ExpectationNotMet:
   expected to find css "title" with text "Sign up" but there were no matches. Also found "", which matched the selector but not all filters.
 # ./spec/features/user_pages_spec.rb:19:in `block (3 levels) in <top (required)>'

2) User pages profile page 
 Failure/Error: it { should have_selector('title', text: user.name) }
 Capybara::ExpectationNotMet:
   expected to find css "title" with text "Michael Hartl" but there were no matches. Also found "", which matched the selector but not all filters.
 # ./spec/features/user_pages_spec.rb:12:in `block (3 levels) in <top (required)>'

Finished in 9.41 seconds
24 examples, 2 failures

Failed examples:

rspec ./spec/features/user_pages_spec.rb:19 # User pages signup page 
rspec ./spec/features/user_pages_spec.rb:12 # User pages profile page 

【问题讨论】:

    标签: ruby-on-rails rspec tdd capybara bdd


    【解决方案1】:

    问题出在这里:

    ./spec/requests/user_pages_spec.rb
    

    您将 Capybara 集成测试放在 requests 文件夹中。这就是 visit 方法不起作用的原因。

    要修复,只需将所有测试从 spec/requests 移动到 spec/features

    【讨论】:

    • @BB500,您需要手动创建该文件夹。您甚至可以在其下创建子文件夹,例如spec/features/models
    • @BB500,请注意/features 文件夹仅用于将使用 Capybara 的集成测试。对于其他功能测试,例如模型、控制器、助手等,您不需要移动它们,它们也不需要像 visit 这样的 Capybara DSL。
    • 谢谢你! - 我将该测试文件移到了一个新的功能文件夹中,并且这些测试通过了。 (当然现在我有几个新的......也许你也能发现这里发生了什么??)我已经编辑了这篇文章。
    • @BB500,你修好了。然后欢迎来到 TDD 世界。您接下来展示的错误是您在 TDD 中最好的朋友,随着您的修复,您构建了功能。如果没有title,请提供标题,如果需要,请提供直到测试通过!
    【解决方案2】:

    发生这种情况是因为您尝试使用来自Capybara::DSLvisit 方法。 如果你检查documentation

    Capybara 不再支持 请求从 Capybara 2.0.0 开始的规格。使用 Capybara 的推荐方法是 具有功能规格。

    要解决此问题,您应该将测试移动到 spec/features 文件夹或包含 Capybara::DSL 以获取请求规范:

    #spec_helper.rb
    RSpec.configure do |config|
      #...
      config.include Capybara::DSL, :type => :request
    

    【讨论】:

    • 谢谢你的帮助。 (显然我没有足够的声誉来“提升”答案
    • 在 Rspec 帮助文件中包含 Capybara,而不是添加新文件夹。工作! +1
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-25
    • 1970-01-01
    • 1970-01-01
    • 2022-11-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多