model_stubbing in Rails 1.2.x

Posted by jacqui maher on April 18, 2008 at 03:58 PM

I really like technoweenie’s plugin model_stubbing. It’s a nice alternative to fixtures, and an even nicer way to create stubs in your tests and specs.

Unfortunately the StreetEasy codebase is still on Rails 1.2.x which caused compatibility problems with the plugin. Rails 2 refactored Fixtures and database statements a bit.

I had to modify the plugin to get it to work with older versions of Rails. I forked the project on github and post about it to help anyone who’d like to use the plugin but is not upgraded to Rails 2 yet.

github homepage: forked model_stubbing
public clone url: git@github.com:jacqui/model_stubbing.git

[edit] btw, simplelog was munging the href for the public clone url; it seems to like prepending http:// to links, so i just removed the anchor tags from it.

Learning StoryRunner

Posted by jacqui maher on January 06, 2008 at 02:53 PM

in which I try to get done with my mockamator already by writing stories describing what it should do, learning how to work with Story Runner in RSpec along the way.

references:
* What’s in a Story by Dan North
* Great step by step example driven tutorial for Rspec on story runner
* RSpec docs on mock objects

This is my first attempt at a story. I already find this helpful as it forces me to make decisions and figure out what it is, exactly, that I’m trying to accomplish. And how.

The Nelson plugin should automagically create mocks (valid or invalid) for any given controller



Narrative:

As a developer
I want to easily write controller specs
So that I’m not spending hours on hundreds of LOC making mocks with the right expectations

Acceptance Criteria:

Scenario 1: writing a new controller spec
Given the UserController
   And that I want to use valid mocks that won’t throw errors
When calling Nelson.generate_mocks(UserController, {:valid => true})
Then a site instance object should be mocked out
   And a get request, for example, on the signup form should not raise an error

Ok, so that’s my story and it’s useful in that it’s already helped me get a better idea of what I’m doing… but how do I translate this into Ruby code that can be run through rspec?

One of the tutorials I’m following gives an example of a story, so I am just going to copy and paste it and change it to be appropriate for my narrative:

   1  Story "The Nelson plugin", %{
2 should automagically create mocks
3 that are valid or invalid
4 for any given controller
5 }, :type => RailsStory do
6
7 Scenario "in the before block of a controller spec" do
8 When "calling Nelson.generate_mocks" do
9 Nelson.generate_mocks(UserController, {:valid => true})
10 end
11
12 Then "a site mock should be generated" do
13 @site.should_not be_nil
14 @site.should be_a_kind_of(Site)
15 end
16
17 When "I request the UserController signup action in a get request" do
18 get '/user/signup'
19 end
20
21 Then "response should be successful" do
22 response.should be_success
23 end
24 end
25 end


That was my first attempt. While writing this a few questions came up, namely…

- does the context get preserved between different When events? that is, will instance variables that are created in one event be accessible in a subsequent event context?
- am i breaking up my tasks correctly?
- what’s up with that array of phrases in the Story block anyway?
- does the When have to be mapped to a controller request?
    (from the vaporbase.com tutorial: “The “When” clause is the meat of the scenario. It is a controller action, and its spec gets done next… “)

Only one way to find out: time to run this through the story runner. I foresee some errors… :)

   1  jm:~/se/app/workspace (master) $ ruby stories/nelson_should_create_mocks.rb 
2 Running 1 scenarios
3
4 Story: The Nelson plugin
5
6
7 should automagically create mocks
8 that are valid or invalid
9 for any given controller
10
11
12 Scenario: in the before block of a controller spec
13
14 When calling Nelson.generate_mocks (FAILED)
15
16 Then a site mock should be generated (SKIPPED)
17
18 When I request the UserController signup action in a get request
19
20 Then response should be successful
21
22 1 scenarios: 0 succeeded, 1 failed, 0 pending
23
24 FAILURES:
25 1) The Nelson plugin (in the before block of a controller spec) FAILED
26 NoMethodError: undefined method `generate_mocks' for Nelson:Class
27 stories/nelson_should_create_mocks.rb:28:in `calling Nelson.generate_mocks'
28 stories/nelson_should_create_mocks.rb:27
29 stories/nelson_should_create_mocks.rb:20


Whoa! That actually went a lot better than I expected. I haven’t written the method “generate_mocks” in my plugin yet, so naturally it would fail.

I love the output of the Story Runner. I think I might be sold. Time to write the methods in my Nelson plugin that will generate the mocks, I guess.

I’ll be posting my stories - when they’re closer to being finalized - here as examples for other people to reference.

In the meantime, here are some:

* from pastie
* from evang.eli.st (scroll down)
* plain text stories from david chelimsky’s blog

quick script to move your test::units to specs

Posted by jacqui maher on December 25, 2007 at 01:25 AM

this isn’t drop dead gorgeous or anything, but it worked ok for what i needed to do in the amount of time i felt like spending on it. i’d love to see how someone would make it better though, as usual.


and argh, i really need to spend some time on the css here. it’s hard to read code i post, and i apologize about that. lame!

download it: teststospecs.rb

view it




upping your test coverage: rspec 1.1 + test unit

Posted by jacqui maher on December 18, 2007 at 10:50 AM

I am going to be looking into RSpec 1.1 in the next couple of days. While we haven’t upgraded our application to run on Rails 2 yet, I am really interested in RSpec’s new integration with Test::Unit.

Right now, we have two rake tasks for ascertaining test coverage using rcov: rake spec:rcov and rake test:rcov. Since one runs our Test::Unit tests, and one runs our RSpec tests, the outcome is far from accurate.

My plan is to hopefully use RSpec’s new integration with Test::Unit to convert all our Test::Unit tests to RSpec - this was, after all, my Big Plan from the beginning. It’s just a lot of work and I dont have that much time. I think this will allow me to move them all into the spec directory and get the total test coverage much more accurately.

I’ll be posting my progress here.

In other news, I’m almost done with the initial version of my automated mock framework plugin - nelson. More on that later as well.

rspec controller syntax

Posted by jacqui maher on November 29, 2007 at 05:26 PM

The rspec docs are great, but the example code for writing Rails controller specs is a little inconsistent.

For future reference, the ‘best way’ to specify your controller is like so:

describe Manage::ListingsController, "manage listings - for the boss" do

the old way, which you shouldn’t use, was like this:

describe "manage listings - for the boss" do controller_name "Manage::Listings"

I ran into a problem specifying my namespaced controller the old way; controller_name calls camelize on the string you pass it after splitting it on the “::” - since we have several ListingsController classes in various namespaces, my spec was sending requests to the wrong ListingsController spec, causing all kinds of failures and sadness.

Thx to the caboose geniuses for helping me out on this one, notably court3nay