Search code examples
ruby-on-railsrspecruby-on-rails-5factory-botrspec-rails

Seeded database key values conflicting with factory bot create/build


Our rails database is pre-seeded with some data for a few of our static models. For example, we have a DocumentType model that gets populated/updated through db/seeds.rb. Users can't modify this model.

This doesn't seem to play nicely with factory_bot, however; when I try to :

create(:document_type)

I get an error stating:

ActiveRecord::RecordNotUnique: PG::UniqueViolation: ERROR: duplicate key value violates unique constraint "document_types_pkey" DETAIL: Key (id)=(1) already exists.

Every time I run the test, this error occurs but the key (id) that is attempted to be save increments. Then, eventually, the test passes when it's outside the range of the seeded data.

What I don't understand is why factory_bot is actually setting the id value and not letting the database assign it when the record is saved.

document_type factory

FactoryBot.define do
  factory :document_type do
    label 'Alien Spacecraft License'
    description 'It should be obvious, I think'
    created_at { Time.now - 30.days }
    updated_at { Time.now - 30.days }
  end
end

attempted fixes

What I have tried is creating a fixture file that imitates exactly what is in the seeds.rb file -- when I do this, factory_bot honors the id values set in the fixture. But it causes a lot of duplicate efforts (I have to keep the seeds in sync with the fixtures).

I have looked at using the fixtures to populate the database but, unfortunately in our case, we are using hard-coded IDs in the seed data to insert/update ... so fixtures don't seem like a good seeding option.

Am curious if anyone has any ideas. Thanks!


Solution

  • Maybe try to sequence your document_type factory id to start increment after the last id of your seed

    FactoryBot.define do
      factory :document_type do
        sequence(:id) {|n| n + 30 } #i.e n + last id known in seed
      end
    end