View Specs: expectations or stubs on ActionView helpers
July 20th, 2009
While adding Textile to a resource following the outside-in BDD process described in the RSpec Book I found myself wanting to put a should_receive expectation on ActionView::Helpers::TextHelper#textilize
This left me somewhat confused, as I wasn't sure what to stub, and the book doesn't cover this. Google also drew a blank.
sticking a <%= inspect %> in the view and looking at the page source revealed an instance of ActionView::Base, which makes sense but was somewhat elusive. It also showed a @controller reference, which itself contains a @template reference. A consequence of this is that in your view spec you can get at the template with @controller.template
It turns out that within a view spec #template provides the relevant object. Thanks to Tim Riley for pointing this out.
For example:
it "should textalize the teaser and extra_content" do
@service = mock_model(Service, :null_object => true)
@service.stub!(:teaser).and_return 'a teaser'
template.stub!(:textilize).and_return "textalised teaser"
template.should_receive(:textilize).with @service.teaser
render
response.should contain("textalised teaser")
end
This kind of stubbing is useful as it checks that the view is calling the textilize method, part of the api, correctly, not whether RedCloth (or some other texitle gem) is doing its thing. Stubbing like this will, if nothing else, speed up the spec execution. Testing with input/output examples for the textilized data could go in the view spec, but api testing at that level seems out of place to me. Of course it should be tested at some level, e.g. with Cucumber. YMMV.
2 Responses to “View Specs: expectations or stubs on ActionView helpers”
Sorry, comments are closed for this article.
Tim Riley Says:
July 22nd, 2009 at 02:15 AM
Hi Nick,
I think you can also access the template object just by using `template` directly in the spec. For example, here’s how we do it in one of our view specs:
Nick Rutherford Says:
July 22nd, 2009 at 10:54 AM
So you can. Thanks for the pointer, I’ll update the post.
Best,
Nick