1

Declaring a class for (fast) testing purposes is great:

require 'fast_helper'
require 'site_search'

class Post; end # This allows not to load the whole Rails env

describe SiteSearch do
  it "searches on posts" do
    Post.stub_chain(:scoped, :by_term).with("ruby").and_return ["post1", "post2"]
    SiteSearch.by_term("ruby").should == ["post1", "post2"]
  end
end

The problem with it is that it seems to break autoloading of rails models when the whole suite of specs is run.

The models aren't loaded anymore when the class gets declared before.

There are 4 ways of injecting the unloaded dependencies:

  1. Declare the class (as in example here)
  2. Set/remove const
  3. Stub a wrapper method
  4. Actually load them

I only want to use the 1st one.

The question: keeping the same specs structure, how can I tell rails to actually load the models even though the class is already declared?

Dmytrii Nagirniak
  • 23,696
  • 13
  • 75
  • 130

1 Answers1

1

In order for your empty class preemption trick to work, you must have set your app config.cache_classes = false, hence eager loading is not happening unless you call

Rails.application.eager_load!

When running the whole test suite you need to make sure classes preload, then empty redefinition should have no effect.

Now the question is how you control that it is run only if the full test suite is called. The honest answer is I don't know, but you can surely control it from the environment. Somewhere in your rspec helpers you initialize rails, update it to something like:

ENV["RAILS_ENV"] ||= 'test'
require File.expand_path("../../config/environment", __FILE__)
require 'rspec/rails'
Rails.application.eager_load! unless ENV["FORCE_EAGER_LOAD"].blank?

and then call rspec on full suite as:

FORCE_EAGER_LOAD=t rspec
Viktor Trón
  • 8,774
  • 4
  • 45
  • 48
  • Thanks Viktor. That seems to do the job. However I'm getting the `warning: already initialized constant MIN_NO_CASH_FLOW_PERIODS` which is probably related to the fact that I sometimes just declare the class, but sometimes I actually `require` it. Thus it is loaded twice now. Any thoughts on it? – Dmytrii Nagirniak Jun 21 '12 at 23:44
  • oops you might need a real ruby wizard then. no clue – Viktor Trón Jun 22 '12 at 00:59
  • That constant is mine and of course I know where it is. It's just the file is loaded twice: 1st time when I call `eager_load!`, the 2nd time when I require that file from an (another) spec. – Dmytrii Nagirniak Jun 22 '12 at 04:13