I'm writing a simple app using rails 4.1.0. I created two models called Serie and Event, with a one to many relationship between them (as in one Serie has many Events).
class Serie < ActiveRecord::Base
has_many :events
end
class Event < ActiveRecord::Base
belongs_to :serie
end
I created the following fixture files for these models:
#series.yml
---
Serie1:
name: Whatever
#events.yml
---
EventSerie11:
date: 2013-01-01
value: '124.4'
serie: Serie1
EventSerie12:
date: 2013-02-01
value: '124.2'
serie: Serie1
The problem is that when I load these fixtures by using rake db:fixtures:load
, I get the wrong foreing keys for the event objects:
$ rails c
Loading development environment (Rails 4.1.0)
2.1.1 :001 > Serie.first.id
Serie Load (0.2ms) SELECT "series".* FROM "series" ORDER BY "series"."id" ASC LIMIT 1
=> 10
2.1.1 :002 > Serie.first.events.count
Serie Load (0.3ms) SELECT "series".* FROM "series" ORDER BY "series"."id" ASC LIMIT 1
(0.2ms) SELECT COUNT(*) FROM "events" WHERE "events"."serie_id" = ? [["serie_id", 10]]
=> 0
2.1.1 :003 > Event.first.serie
Evento Load (0.2ms) SELECT "events".* FROM "events" ORDER BY "events"."id" ASC LIMIT 1
Serie Load (0.3ms) SELECT "series".* FROM "series" WHERE "series"."id" = ? LIMIT 1 [["id", 627975337]]
=> nil
2.1.1 :004 > Evento.first.serie_id
Evento Load (0.4ms) SELECT "eventos".* FROM "eventos" ORDER BY "eventos"."id" ASC LIMIT 1
=> 627975337
So you see that all fixtures are loading, but the Event records are being assigned an incorrect serie_id foreign key (and since I'm using sqlite for development there are no constraint checks). As far as I can tell, each time I reset the database and load the fixtures, the Serie record gets a new id, but the serie_id field of each Event record is always set to 627975337.
I read here that you can specify the load order for your fixtures; however adding the line
ENV["FIXTURES"] ||= "series,events"
to my environment.rb file didn't work, nor did running
rake db:fixtures:load FIXTURES=series,events
Any ideas?
I think rails is getting in a muddle with your class/fixtures name for series
. It tries to look for a model class named Series
because it struggles to singularize your plural name. (Series being a word in english where the plural is the same as the singular).
I strongly suspect that the Serie
instance in your database is nothing to do with your fixture load at all and is instead an instance that has been created via another method.
The serie_id
used in your events fixtures is correct. The id that is used is calculated using:
> ActiveRecord::FixtureSet.identify(:Serie1)
=> 627975337
which you can see is the same as the value used in your fixtures.
So, a solution, you can either get into the bowels of active record and override the rake task that loads the fixtures - or you can define your singular/plural versions of "serie"/"series" to be what you want rather than what rails is guessing. In config/application.rb
or an initializer you can add:
ActiveSupport::Inflector.inflections do |inflect|
inflect.irregular 'serie', 'series'
end
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With