#has_content?(String)总是返回false

时间:2014-04-29 09:55:44

标签: ruby-on-rails ruby rspec capybara

我的rspec测试存在问题,特别是使用has_content方法。以下是一些代码段。我一直在关注Michael Hartl的Ruby on Rails教程,以防你不知道。

即使微博设置了各自的内容,

has_content也总是返回false。

结果测试

Run options: include {:line_numbers=>[61]}
..FFF

Failures:

1) User pages profile page microposts should have content 0
 Failure/Error: it { should have_content(user.microposts.count) }
   expected #has_content?(0) to return true, got false
 # ./spec/requests/user_pages_spec.rb:72:in `block (4 levels) in <top (required)>'

2) User pages profile page microposts should have content "Foo Bar"
 Failure/Error: it { should have_content(m2.content) }
   expected #has_content?("Foo Bar") to return true, got false
 # ./spec/requests/user_pages_spec.rb:71:in `block (4 levels) in <top (required)>'

3) User pages profile page microposts should have content "Lorem Ipsum"
 Failure/Error: it { should have_content(m1.content) }
   expected #has_content?("Lorem Ipsum") to return true, got false
 # ./spec/requests/user_pages_spec.rb:70:in `block (4 levels) in <top (required)>'

Finished in 0.74407 seconds
5 examples, 3 failures

Failed examples:

rspec ./spec/requests/user_pages_spec.rb:72 # User pages profile page microposts should      have content 0
rspec ./spec/requests/user_pages_spec.rb:71 # User pages profile page microposts should have content "Foo Bar"
rspec ./spec/requests/user_pages_spec.rb:70 # User pages profile page microposts should have content "Lorem Ipsum"

Randomized with seed 43497

[Finished in 1.3s with exit code 1]

user_pages_spec.rb

describe "profile page" do
    let(:user) { FactoryGirl.create(:user) }
    let(:m1) { FactoryGirl.create(:micropost, user: user, content: "Lorem Ipsum") }
    let(:m2) { FactoryGirl.create(:micropost, user: user, content: "Foo Bar") }

    before { visit user_path(user) }

    it { should have_selector('h1', text: user.name) } 
    it { should have_title(full_title(user.name)) }

    describe "microposts" do
        it { should have_content(m1.content) }
        it { should have_content(m2.content) }
        it { should have_content(user.microposts.count) }
    end
end

show.hml.erb

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

<div class='row'>
    <aside class='col-md-4'>
        <section>
            <h1>
                <%= gravatar_for @user, size: 50 %>
                <%= @user.name %>
            </h1>
        </section>
    </aside>

    <div class="col-md-8">
        <% if @user.microposts.any? %>
            <h3>Microposts (<%= @user.microposts.count %>)</h3>.
            <ol class="microposts">
                <%= render @microposts %>
            </ol>
        <% end %>
    </div>
</div>

_micropost.html.erb

<li>
    <span class="content">
        <%= micropost.content %>
    </span>
    <span class="timestamp">
        Posted <%= time_ago_in_words(micropost.created_at) %>
    </span>
</li>

micropost.erb

class Micropost < ActiveRecord::Base
    attr_accessible :content
    belongs_to :user

    validates :user_id, presence: true
    validates :content, presence: true, length: { maximum: 140 }

    default_scope { order('microposts.created_at DESC') }
end

user.rb

class User < ActiveRecord::Base
    attr_accessible :name, :email, :password, :password_confirmation
    has_secure_password
    has_many :microposts, dependent: :destroy

    # remaning lines are for validation

end

===编辑(回答问题)===

我用过了!而是在每个例子之前强制调用方法。

let!(:m1) { FactoryGirl.create(:micropost, user: user, content: "Lorem Ipsum") }
let!(:m2) { FactoryGirl.create(:micropost, user: user, content: "Foo Bar") }

1 个答案:

答案 0 :(得分:1)

let方法定义了一个带给定块的方法,因此每次拨打user时都会创建一个新方法,每次拨打m1m2时都会创建带有新用户的新微博。而是做:

before(:each) do
  @user = FactoryGirl.create(:user)
  @m1 = FactoryGirl.create(:micropost, user: user, content: "Lorem Ipsum")
  @m2 = FactoryGirl.create(:micropost, user: user, content: "Foo Bar")

  visit user_path(@user) 
end

// Use the instance variables in your tests, or wrap them in methods:
let(:user) { @user }
let(:m1) { @m2 }
let(:m2) { @m1 }