Factory_Girl Sequences as Lazy Attributes
I just ran into a problem with factory_girl sequences. The problem was I defined my Factories like this:
1 2 3 4 5 6 7 8 9 10 11 12 |
# Sequences Factory.sequence :name do |n| 'name' + n.to_s end # Manufacturers Factory.define :manufacturer do |m| m.name Factory.next(:name) m.active true end |
Assume I have a validates_uniqueness_of validation on name in Manufacturer:
1 2 3 4 5 |
class Manufacturer < ActiveRecord::Base validates_uniqueness_of :name end |
Now, lets say I created a couple of manufacturers in my test setup:
1 2 3 4 5 6 7 8 9 |
require File.dirname(__FILE__) + '/../test_helper' class ProductTest < ActiveSupport::TestCase setup do 2.times { Factory(:manufactuer) } end end |
Ok, this setup block will fail because it's creating 2 manufacturers with the same name. But, I thought I was using a sequence? Well, the sequence is only sequenced during the definition of the factories. Meaning, in the above example Factory#next was only called once.
Luckily, factory_girl allows us to use something called lazy attributes. We can just wrap our sequence with some curly brackets, like so:
m.name { Factory.next(:name) } |
Now everytime I create a new Manufacturer the sequence will generate a unique name. Nice! Maybe if I'd taken some more time to RTFM, I wouldn't have wasted time on this problem. Regardless, I thought maybe I'd be able to help someone else out that runs into this.
More about factory_girl
jason said
Dec 19, 2008 @ 02:12 AM
Thanks, it helped me, I missed it too. I think the docs aren't clear enough about this though.Matt Van Horn said
Jul 12, 2009 @ 07:13 AM
Thanks, it got me too.