无法为Rails创建RSpec的头部和尾部

时间:2012-08-12 19:27:08

标签: ruby-on-rails rspec

我有一套测试用于搜索名字的导演,这些测试暂时或多或少地为我工作。沿着:

describe MoviesController do
  before :each do
    @fake_results = [mock(Movie),mock(Movie)]
  end
  it "should call the model that looks for same director movies" do
    Movie.should_receive(:find_by_same_director).with('Woody Allen').and_return(@fake_results)
    post :find_by_same_director, {:name => 'Woody Allen'}
  end

等等。这并没有太令人震惊的破坏。不幸的是我然后决定我需要更改我的控制器方法以获取id参数,而不是名称。我的代码的第二部分现在看起来像:

it "should call the model that looks for same director movies" do
  Movie.should_receive(:find_by_same_director).with(:id => 1).and_return(@fake_results)
  post :find_by_same_director, {:id => 1}
end

现在运行规范会导致以下错误:

  1) MoviesController finding movies with same director should call the model method that looks for same director movies
     Failure/Error: post :find_by_same_director, {:id => 1}
     ActiveRecord::RecordNotFound:
       Couldn't find Movie with id=1
     # ./app/controllers/movies_controller.rb:62:in `find_by_same_director'
     # ./spec/controllers/movie_controller_spec.rb:12:in `block (3 levels) in <top (required)>'

为什么缺少一个id = 1的真实电影现在导致严重的错误 - 我的存根/模拟不再覆盖我了吗?之前没有Woody Allen执导的电影。我需要做些什么来让我的测试能够令人满意地假装存在id为1的电影?

编辑:

控制器操作如下:

  def find_by_same_director
   @movie = Movie.find params[:id]
   @movies = Movie.find_same_director(@movie.id)
   if @movies.count == 1
    flash[:notice] = "'#{@movie.title}' has no director info"
    redirect_to movies_path
   end
  end

不确定这是否需要哈希值??

1 个答案:

答案 0 :(得分:1)

控制器是否使用散列或整数id在find_by_same_director模型上调用Movie方法?如果它是后者那么你设置它的模拟将不起作用,因为你指定必须使用has {:id => 1}来调用它,所以你需要将它改为:

Movie.should_receive(:find_by_same_director).with(1).and_return(@fake_results)

如果确实使用with指定了模拟期望值,则传递的参数必须完全匹配。如果它们不匹配,则将调用未模拟的find_by_same_director方法。如果你想为任何参数模拟一个方法,那么你可以完全忽略with

Movie.should_receive(:find_by_same_director).and_return(@fake_results)

编辑:

查看控制器操作,您需要模拟Movie.find方法以及find_same_director

Movie.should_receive(:find).with('1').and_return(mock_model(:id => 1))

或者只是存根(如果你不想断言该方法被调用):

Movie.stub(:find).and_return(mock_model(:id => 1))

我还注意到规范模仿find_by_same_director方法,而控制器调用find_same_director。这只是一个错字吗?