[rspec-users] issue with application controller spec

Craig Jolicoeur cpjolicoeur at gmail.com
Sat Sep 6 15:30:10 EDT 2008


I think part of my problem, now that I think about it, is that I'm
trying to test the method instead of testing behavior.  This
render_403 method should probably not be tested directly from the
application_controller_spec since it doesnt get actually called
their.  I should test the render method from the controllers where the
behavior is actually expected since it makes more sense.

Thanks for all the help

On Sep 6, 11:00 am, "David Chelimsky" <dchelim... at gmail.com> wrote:
> On Sat, Sep 6, 2008 at 9:15 AM, Craig Jolicoeur <cpjolico... at gmail.com> wrote:
> > Thanks David.
>
> > I changed to using get :render_403 and it worked.  Well, worked after
> > I added in those routes to my routes.rb file.
>
> > I dont have the default routes for /:controller/:action/:id so it was
> > failing and I dont want custom routes for these two methods because
> > they will be called from other controllers directly and don't need a
> > named route.
>
> > What is the proper way to test application controller methods that get
> > called from other controllers?
>
> The problem to solve here is the fact that Rails is providing a bunch
> of setup for us when we go through an action, and the render method in
> the controller relies on that setup.
>
> There are (at least) two ways you could go here, neither of which is
> perfect, but perhaps you'll like them better than what you're doing.
>
> One would be to set a message expectation on render:
>
> controller.should_receive(:render).with(:file =>
> "#{RAILS_ROOT}/public/403.html", :status => '403')
> controller.get_403
>
> That's a very implementation specific approach, and this is the sort
> of thing that leads to endless debate over the costs/benefits of
> mocking/stubbing. In this particular case, though, it'll get you the
> answer you're looking for.
>
> Another approach is to create a fake controller:
>
> class FakeController < ApplicationController
>   def action_that_raises_a_403
>     get_403
>   end
> end
>
> and add routing for this controller only if ENV['RAILS_ENV'] == 'test'
> (in spec_helper or somewhere in the spec directory).
>
> For that matter, you could just add routing for get_403 directly, but
> because it itself is not really an action, but a helper, it might be
> more clear to not call it directly, but only from an action.
>
> HTH,
> David
>
>
>
> > I will never manually go to /
> > application/render_403 but it seems I had to pretend this would happen
> > to spec it out properly.
>
> > - Craig
>
> > On Sep 6, 9:55 am, Craig Jolicoeur <cpjolico... at gmail.com> wrote:
> >> >>First off - should_receive *is* a test - why would you write a test in
>
> >> the setup?
>
> >> Not sure what you mean by that.  I'm not writing a test in the setup
> >> routine.
>
> >> Also, I'm not setting an expectation on a method call.  should
> >> render_file is in the right place.
>
> >> On Sep 5, 11:48 pm, Scott Taylor <mailing_li... at railsnewbie.com>
> >> wrote:
>
> >> > On Sep 5, 2008, at 10:18 PM, Craig P Jolicoeur wrote:
>
> >> > > I'm having some trouble trying to spec some methods in my Rails
> >> > > application controller.
>
> >> > > I'm new to rspec converting over from straight test::unit.
>
> >> > > Here is the method in my application.rb controller that I'm trying
> >> > > to spec
>
> >> > >  def render_403
> >> > >    logger.debug "Returned 403: #{request.request_uri}"
> >> > >    render :file => "#{RAILS_ROOT}/public/403.html", :status => '403'
> >> > >  end
>
> >> > > Here is my *current* spec
>
> >> > >  describe "handling render 403" do
>
> >> > >    before(:each) do
>
> >> > > controller.request.should_receive(:request_uri).and_return('response
> >> > > request_uri')
> >> > >    end
>
> >> > First off - should_receive *is* a test - why would you write a test in
> >> > the setup?
>
> >> > >    it "should render the 403 error page" do
> >> > >      controller.render_403
> >> > >      response.should render_file("#{RAILS_ROOT}/public/403.html")
> >> > >    end
>
> >> > Two issues with this test:
>
> >> > 1.  Normally, if you are going to write a test checking that a method
> >> > is called on an object (should_receive), you'd write that assertion
> >> > before you perform any action.  For example:
>
> >> > an_object.should_receive(:a_method_call)
> >> > an_object.a_method_call
>
> >> > would pass
>
> >> > but
>
> >> > an_object.a_method_call
> >> > an_object.should_receive(:a_method_call)
>
> >> > would fail
>
> >> > 2. Usually, you make a request in controller specs, like
> >> > "get :render_404".  See the controller docs on the rspec site.
>
> >> > Hope that helps,
>
> >> > Scott
>
> >> > _______________________________________________
> >> > rspec-users mailing list
> >> > rspec-us... at rubyforge.orghttp://rubyforge.org/mailman/listinfo/rspec-users
>
> >> _______________________________________________
> >> rspec-users mailing list
> >> rspec-us... at rubyforge.orghttp://rubyforge.org/mailman/listinfo/rspec-users
> > _______________________________________________
> > rspec-users mailing list
> > rspec-us... at rubyforge.org
> >http://rubyforge.org/mailman/listinfo/rspec-users
>
> _______________________________________________
> rspec-users mailing list
> rspec-us... at rubyforge.orghttp://rubyforge.org/mailman/listinfo/rspec-users


More information about the rspec-users mailing list