Search code examples
rubyfunctional-testingruby-mocha

Mocha Mock Carries To Another Test


I have been following the 15 TDD steps to create a Rails application guide - but have run into an issue I cannot seem to resolve. For the functional test of the WordsController, I have the following code:

class WordsControllerTest < ActionController::TestCase
  
  test "should get learn" do
    get 'learn'
    assert_response :success
  end

  test "learn passes a random word" do    
    some_word = Word.new
    Word.expects(:random).returns(some_word)
    get 'learn'
    assert_equal some_word, assigns('word')
  end
end

In the Word class I have the following code:

class Word < ActiveRecord::Base
  def self.random
    all = Word.find :all
    all[rand(all.size)]
  end
end

When I run the tests, I experience the following error (shortened for brevity):

1) Failure: unexpected invocation: Word(...).random() satisfied expectations:
- expected exactly once, already invoked once: Word(...).random()

I have tried changing changing the order of the tests along with a multitude of other things, but time and time again I continue to receive the same test failure - that Word.random() has already been invoked.

I'm running Rails 3.0 beta 4 and Mocha 0.9.8. I've searched long and hard for a solution to my problem, but I can't seem to find it. I'm new to Ruby/Rails so am rather unfamiliar with the language and the frameworks.

Thanks in advance!


Solution

  • I had the same problem, mocked functionality was not isolated to a test, it seems to be a problem with the load order of Mocha.

    I had some issues getting Mocha to work with Rails3. I found a few stackoverflow posts regarding, but didn't stumble across the solution until I found a post on agoragames.com

    Basically, in the Gemfile of your project, the require for Mocha should look like:

    gem 'mocha', :require => false
    

    Then in test/test_helper.rb, add a require line for mocha:

    ...
    ...
    require File.expand_path('../../config/environment', __FILE__)
    require 'rails/test_help'
    require 'mocha'
    
    class ActiveSupport::TestCase
    ...
    ...
    

    I think the require line for mocha in the Gemfile means that you need to already have mocha installed as a gem, bundler won't take care of it for you.