I am writing Rspec test for a Ruby On Rails engine. My engine provide ActiveRecord models with a class method is_a_limesurvey_participant(opts = {})
that extends them with class variables and associations. To test my TestModel extension I need to initialize it multiple times in different and consecutive RSpec contexts providing different options. To do so I need to undefine my TestModel otherwise it will "remember" old settings. I do that calling the following utility method before test inspired by this:
def reset_test_model
Object.send(:remove_const,'TestModel')
load File.join(ENGINE_RAILS_ROOT,'spec','dummy','app','models','test_model.rb')
end
And that's ok.
Here's the problem. My engine has a model (SurveyParticipation) which need to be related to my main app TestModel with an association. I do this in my is_a_limesurvey_participant method this way:
def is_a_limesurvey_participant(opts = {})
# ... class variables definitions
has_many :survey_participations, :class_name => "LimesurveyRails::SurveyParticipation", :foreign_key => "participant_id"
LimesurveyRails::SurveyParticipation.belongs_to :participant, :class_name => self.name, :foreign_key => 'participant_id'
puts (LimesurveyRails::SurveyParticipation.reflect_on_association(:participant).klass.object_id == self.object_id)
end
I expected the puts call to always show me true for any examples each time my TestModel call is_a_limesurvey_participant method because LimesurveyRails::SurveyParticipation.reflect_on_association(:participant).klass should be the current TestModel and so it is if I run my test separately.
But running my tests all together show me that LimesurveyRails::SurveyParticipation.reflect_on_association(:participant).klass references always the same TestModel object, that is, the one which was the current one the first time Rspec ran is_a_limesurvey_participant method.
If I try to retrieve both objects by object_id I can see that they both exist in the ObjectSpace:
(rdb:1) ObjectSpace._id2ref(70222826866840)
TestModel(id: integer, name: string, surname: string, email_address: string, extra_id: string, created_at: datetime, updated_at: datetime)
(rdb:1) ObjectSpace._id2ref(70222827277420)
TestModel(id: integer, name: string, surname: string, email_address: string, extra_id: string, created_at: datetime, updated_at: datetime)
I also tried to do the same reset_test_model trick for LimesurveyRails::SurveyParticipation class but even if it gets replaced, the same doesn't happen for its referenced class in the :participant association
In few words belongs_to, after the first call, retrieve the first/wrong/cancelled/unreferenced TestModel. Apart from this situation what is a good pattern to test different class configurations with Rspec? Of course running the test separately makes all working fine, is this the right pattern?