[rspec-users] Mock or Stub strategy for validates_uniqueness_of

Daniel N has.sox at gmail.com
Wed Jul 25 06:31:33 EDT 2007


On 7/25/07, Mikel Lindsaar <raasdnil at gmail.com> wrote:
>
> Kyle,
>
> That is a good point.  We are after the behaviour, not the implementation.
>
> Regards
>
> Mikel
>
> On 7/25/07, Daniel N <has.sox at gmail.com> wrote:
> >
> >
> >
> > On 7/25/07, Kyle Hargraves <philodespotos at gmail.com> wrote:
> > > Daniel N wrote:
> > > > On 7/25/07, Mikel Lindsaar <raasdnil at gmail.com> wrote:
> > > >>
> > > >> There would be a different way.
> > > >>
> > > >> In the idea of "Only test the code you write" all you really need
> to
> > > >> spec is that you have set the right association, because
> activerecord
> > > >> has it's own tests to ensure the uniq call works.
> > > >>
> > > >> You can do this with a call to
> > reflect_on_association.  Unfortunately
> > > >> that call does not return a hash, but an association object.
> > > >>
> > > >> I wrote a blog post on how to do this easily with a spec_helper.rb
> > > >> method that adds to_hash to reflect on association.
> > > >>
> > > >>
> > > >>
> >
> http://www.blognow.com.au/q/67540/Reflect_on_association_one_liner_to_check_association_details.html
> > > >>
> > > >>
> > > >> In the end you end up with a spec that looks like this:
> > > >>
> > > >> it "should test reflection details" do
> > > >>
> > > >>     association_results = {
> > > >>       :macro => :has_many,
> > > >>       :options => {:through => :clipping, :uniq => true},
> > > >>       :class_name => "nil"
> > > >>     }
> > > >>
> > > >>     Book.reflect_on_association (:clip).to_hash.should ==
> > > >> association_results
> > > >>
> > > >>   end
> > > >>
> > > >>
> > > >> Of course, you can add whatever values you want into the hash.
> > > >>
> > > >> I now have one of these specs at the top of pretty much every model
> > > >> spec.  Just set up the hash with all your association rules and
> then
> > > >> this can be checked and kept track of when you are refactoring or
> > > >> changing code.
> > > >>
> > > >> Hope that helps.
> > > >>
> > > >> Regards
> > > >>
> > > >> Mikel
> > > >
> > > >
> > > > Thanx Mikel.
> > > >
> > > > I didn't even think of using a uniq on the has_many.  I was using a
> > > > validates_uniquness_of :scope => 'book_id'
> > > >
> > > > I will definitley look into this one.
> > > >
> > > > Thankyou
> > > > Daniel
> > >
> > > However you decide to go about solving it, the idiom you hit upon is
> > > what, to me, actually describes the behaviour; if the book already has
> a
> > > clip once, you can't add it again:
> > >
> > >    lambda { add_twice }.should change(...).by(1)
> > >
> > > It states very clearly what results you wish to see.
> > >
> > > Going through reflect_on_association feels too much like specifying
> the
> > > use of a particular implementation, rather than the desired outcome.
> > >
> > > Kyle
> >
> >
> >  It looks much better when you write it like that though ;)
> >
> >
> >


Thanx for the input guys.  I wasn''t entirely happy with what I had because
it didn't actually test what I wanted.  It tests that a duplicate cannot be
added.  But I specifically wanted to not allow duplicates for a given
clip_id

  it "should have a uniq clip_id for a given book" do
    lambda do
      Clipping.create( valid_clipping_attributes )
      Clipping.create( valid_clipping_attributes )
    end.should change( Clipping, :count ).by( 1 )
  end

became

  it "should have a uniq clip_id for a given book" do
    lambda do

      Clipping.create( valid_clipping_attributes.with( :book => @book, :clip
=> @clip ) )
      clipping = Clipping.create( valid_clipping_attributes.with( :book =>
@book, :clip => @clip ) )

      clipping.should have(1).error_on( :clip_id )
      clipping.errors.on( :clip_id ).should match(
/(already|duplicate|exists)/i )

    end.should change( Clipping, :count ).by( 1 )
  end

If anyone was interested :P

Daniel
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://rubyforge.org/pipermail/rspec-users/attachments/20070725/db8d118b/attachment.html 


More information about the rspec-users mailing list