[rspec-users] Mocking, changing method interfaces and integration tests

Courtenay court3nay at gmail.com
Fri May 25 18:23:46 EDT 2007

On 5/25/07, David Chelimsky <dchelimsky at gmail.com> wrote:
> As for mocks tying you to implementation - I see a strong relationship
> to how well you follow "Tell, Don't Ask" and the value you get out of
> mocking. If you're doing a lot telling instead of asking, you have an
> implicitly more loosely coupled design. But if you want to make sure
> that the object being described does the telling, there's no better
> way to do that then with a mock in my view.

David, Pat, Ruy:

I think this is a failure of Rails for letting us talk to the DB from
our controllers. For example

  def show
     @user = User.find(:first, :conditions => { :id => params[:id] },
:include => :images)

This kind of thinking then pervades throughout the entire 'rails way'
of doing things.

This makes it hard to refactor, and just horrible to mock.  I can
never think up a catchy name for this, (i'll use find_inclusive for
now) but ...

  def show
    @user = User.find_inclusive( params[:id] )

This works on the idea that, "What if 'find' were a private method?"

Now we can mock User.find_inclusive in the controller spec; we can
refactor the entire user model, change the database implementation
(:include something else) and, in an extreme case, you only give an
external coder access to particular models knowing that other code
wouldn't be touched (yes, I've done this in the past. Yuk.)

Now, on a large or distributed team, hell.. any size team.. if someone
goes and changes find_inclusive, and the user-model spec breaks, they
are responsible for ensuring that the failing spec is NOT altered;
rather, that their code respects the old API and the spec passes, in
addition to their fixes.

Finally, higher-level tests (whether selenium or rails' integrations)
will help you test the whole stack; I still don't believe that
controllers should_hit the db :)


More information about the rspec-users mailing list