factory_girl callbacks & validating presence of associated records

There is a Mission model which has_many: supplier_assignments, and every mission should have at least one supplier_assignment at all times.

I wrote an RSpec test for this as follows:

...
  let (:mission) { create(:mission) }
...
  it "has at least one supplier_assignment" do
    mission.supplier_assignments.each do |sa|
      sa.destroy!
    end
    mission.reload.should_not be_valid
  end
...
 

And I defined my factory to automatically create an associated supplier_assignment each time it creates a mission:

  FactoryGirl.define do
    factory :mission do |f|
    ...
      after(:build) do |m|
        m.supplier_assignments << build(:supplier_assignment, mission: m)
      end
    end
  end

Above, I explicitly state mission: m in build(:supplier_assignment, mission: m). Stating it explicitly fixed a problem I had where my test suite slowed to a crawl, and I was getting a “stack level too deep” error. It was obvious in retrospect that this was needed, but I did not realize it until I read this blog post by Tim Riley

I also refactored models with a belongs_to association. For example, in my SupplierAssignment model, I changed

validates :mission_id, presence: true

to

validates :mission, presence: true

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s