1

最近、最初のRails3アプリにDeviseを追加しましたが、コントローラーのテストで少し問題が発生しています。

Deviseが使用しているのと同じモデルであるUserコントローラークラスをテストしています。だから私のスペックの初めに私はこれを持っています:

before(:each) do
  sign_in @user = Factory.create(:user)
end

これで、次のようにモックやスタブを使用せずにテストに合格できます。

describe "GET edit" do
  it "assigns the requested user as @user" do
    user = Factory(:user)
    get :edit, :id => user.id
    assigns(:user).should eql(user)
  end
end

しかし、教育目的で、モックとスタブで動作させる方法を知りたいのですが、通常は完全に簡単ですが、DeviseがUser.findコントローラーのアクションの前に呼び出して、テストを失敗させているようです。

describe "GET edit" do
  it "assigns the requested user as @user" do
    user = Factory(:user)
    User.expects(:find).with(:first, :conditions => {:id => 37}).returns(user)
    get :edit, :id => '37'
    assigns(:user).should be(user)
  end
end

また、期待値に追加twiceすると、最初のfindの呼び出しが、期待値を設定している呼び出しとは異なるため、これも失敗します。

任意の洞察をいただければ幸いです。

4

1 に答える 1

5

stubs次のいずれかまたはいずれかを使用して、複数の戻り値を指定できますexpects

require 'test/unit'
require 'mocha'

class Foo
end

class FooTest < Test::Unit::TestCase

  # This passes!
  def test_multiple_returns_with_stubs
    Foo.stubs(:find).returns('a').returns('b').returns('c')

    assert_equal('a', Foo.find('z'))
    assert_equal('b', Foo.find('y'))
    assert_equal('c', Foo.find('x'))
  end

  # This passes too!
  def test_multiple_returns_with_expects
    Foo.expects(:find).times(1..3).returns('a').returns('b').returns('c')

    assert_equal('a', Foo.find('z'))
    assert_equal('b', Foo.find('y'))
    assert_equal('c', Foo.find('x'))
  end
end

違いは、明らかに、それexpectsが何回呼び出されるかを知る必要があるということです。何も指定しない場合はonce、後続の呼び出しを想定して文句を言います。stubs気にしない。

于 2010-07-29T20:24:02.750 に答える