Hi,
I have a project that I had running under rspec 0.6.x and recently upgraded
to 0.7.2.
I am trying to isolate my controllers from the database as I go through and
change all the specs to run under 0.7.2.
I am having a problem where I need to make the create! method return the
mocked object as well as raise RecordInvalid exception. Is this at all
possible?
I use the rescue statement in my controller methods and not @
object.new_record? or @object.valid? to check whether to redirect or render.
-- controller --
def create
@star = Star.create!(params[:star])
redirect_to star_path(@star)
rescue ActiveRecord::RecordInvalid
render :action => ''new''
end
-- spec --
@star = mock(''star'')
Star.should_receive(:create!).with({ ''name'' => nil
}).and_return(@star)
I''m new to all the mocking/stubbing business so my head spins are
turning
into headaches. :)
Dylan.
-------------- next part --------------
An HTML attachment was scrubbed...
URL:
http://rubyforge.org/pipermail/rspec-users/attachments/20061122/9c0bfc6f/attachment.html
On 11/21/06, Dylan Egan <dylanegan at gmail.com> wrote:> Hi, > > I have a project that I had running under rspec 0.6.x and recently upgraded > to 0.7.2. > > I am trying to isolate my controllers from the database as I go through and > change all the specs to run under 0.7.2. > > I am having a problem where I need to make the create! method return the > mocked object as well as raise RecordInvalid exception. Is this at all > possible?AFAIK, Ruby won''t let you return an object and raise an error at the same time. You get one or the other.> I use the rescue statement in my controller methods and not @ > object.new_record? or @object.valid? to check whether to redirect or render. > > -- controller -- > > def create > @star = Star.create!(params[:star]) > redirect_to star_path(@star) > rescue ActiveRecord::RecordInvalid > render :action => ''new'' > end > > -- spec -- > @star = mock(''star'') > Star.should_receive(:create!).with({ ''name'' => nil }).and_return(@star)Hmmm. As I said above, I can''t imagine that Ruby will let you do that. What I would do in this case is this: -- spec -- @star = mock(''star'') Star.should_receive(:create!).with({ ''name'' => nil }).and_raise(ActiveRecord::RecordInvalid) Star.should_receive(:create).with({ ''name'' => nil }).and_return(@star) -- controller -- def create @star = Star.create!(params[:star]) redirect_to star_path(@star) rescue ActiveRecord::RecordInvalid @star = Star.create(params[:star]) render :action => ''new'' end OR def create @star = Star.create!(params[:star]) redirect_to star_path(@star) rescue ActiveRecord::RecordInvalid render :action => ''new'' end def new @star = Star.new end> I''m new to all the mocking/stubbing business so my head spins are turning > into headaches. :)Hope that helps. David> Dylan. > > _______________________________________________ > rspec-users mailing list > rspec-users at rubyforge.org > http://rubyforge.org/mailman/listinfo/rspec-users > >
As far as your controller action goes, you might try switching from
the exception handling way of rendering different actions to using
something like:
def create
@star = Star.new(params[:star])
if @star.save
redirect_to star_path(@star)
else
render :action => ''new''
end
This keeps your @star object available even when it is invalid, which
gives you the ability to use "error_messages_for
''star''" in your
new.rhtml. It should also make specing easier. I basically cribbed it
from scaffold_resource, so it''s also the core-team blessed way.
I used to use the exception handling method, but because @star.save
returns false on failure, there''s no reason to have other checks. It
also gives you the ability to do more stuff to @star after it''s been
initialized but before it has to be valid. Now I''m fully a convert to
the @star.save conditional structure.
Hope this helps.
Chris
On 11/22/06, David Chelimsky <dchelimsky at gmail.com>
wrote:> On 11/21/06, Dylan Egan <dylanegan at gmail.com> wrote:
> > Hi,
> >
> > I have a project that I had running under rspec 0.6.x and recently
upgraded
> > to 0.7.2.
> >
> > I am trying to isolate my controllers from the database as I go
through and
> > change all the specs to run under 0.7.2.
> >
> > I am having a problem where I need to make the create! method return
the
> > mocked object as well as raise RecordInvalid exception. Is this at all
> > possible?
>
> AFAIK, Ruby won''t let you return an object and raise an error at
the
> same time. You get one or the other.
>
> > I use the rescue statement in my controller methods and not @
> > object.new_record? or @object.valid? to check whether to redirect or
render.
> >
> > -- controller --
> >
> > def create
> > @star = Star.create!(params[:star])
> > redirect_to star_path(@star)
> > rescue ActiveRecord::RecordInvalid
> > render :action => ''new''
> > end
> >
> > -- spec --
> > @star = mock(''star'')
> > Star.should_receive(:create!).with({ ''name'' =>
nil }).and_return(@star)
>
> Hmmm. As I said above, I can''t imagine that Ruby will let you do
that.
> What I would do in this case is this:
>
> -- spec --
> @star = mock(''star'')
> Star.should_receive(:create!).with({ ''name'' => nil
> }).and_raise(ActiveRecord::RecordInvalid)
> Star.should_receive(:create).with({ ''name'' => nil
}).and_return(@star)
>
> -- controller --
>
> def create
> @star = Star.create!(params[:star])
> redirect_to star_path(@star)
> rescue ActiveRecord::RecordInvalid
> @star = Star.create(params[:star])
> render :action => ''new''
> end
>
> OR
>
> def create
> @star = Star.create!(params[:star])
> redirect_to star_path(@star)
> rescue ActiveRecord::RecordInvalid
> render :action => ''new''
> end
>
> def new
> @star = Star.new
> end
>
> > I''m new to all the mocking/stubbing business so my head spins
are turning
> > into headaches. :)
>
> Hope that helps.
>
> David
>
> > Dylan.
> >
> > _______________________________________________
> > rspec-users mailing list
> > rspec-users at rubyforge.org
> > http://rubyforge.org/mailman/listinfo/rspec-users
> >
> >
> _______________________________________________
> rspec-users mailing list
> rspec-users at rubyforge.org
> http://rubyforge.org/mailman/listinfo/rspec-users
>
--
Chris Anderson
http://jchris.mfdz.com
Heya, Yeah I might just have to revert back to the way I used to do it. I liked the rescue way because it was a much tidier presentation. Also I have the new/create methods, just like anyone using REST and the .and_raise bit didn''t work. Or I could just use the DB on these cases. Choices choices. Thanks anyways. Dylan. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://rubyforge.org/pipermail/rspec-users/attachments/20061123/187606ab/attachment.html