我有一个模型 contact
,它 has_many :locations,通过: :relationships
,以及 has_many :teams,通过: :contacts_teams
。
联系人必须拥有关联的团队
和位置
才能通过验证。换句话说:新的联系人
必须具有关联的relationship
记录和关联的contacts_team
记录。以下为型号:
#models/contact.rb
class Contact < ActiveRecord::Base
has_many :contacts_teams
has_many :teams, through: :contacts
has_many :relationships, dependent: :destroy
has_many :locations, through: :relationships
accepts_nested_attributes_for :contacts_teams, allow_destroy: true
# upon create, validate that at least one associated team and one associated location exist
validate :at_least_one_contacts_team
validate :at_least_one_relationship
private
def at_least_one_contacts_team
return errors.add :base, "Must have at least one Team" unless contacts_teams.length > 0
end
def at_least_one_relationship
return errors.add :base, "Must have at least one Location" unless relationships.length > 0
end
end
#models/contacts_team.rb
class ContactsTeam < ActiveRecord::Base
belongs_to :contact
belongs_to :team
end
#models/team.rb
class Team < ActiveRecord::Base
has_many :contacts_teams
has_many :contacts, through: :contacts_teams
end
#models/relationship.rb
class Relationship < ActiveRecord::Base
belongs_to :contact
belongs_to :location
end
#models/location.rb
class Location < ActiveRecord::Base
has_many :relationships
has_many :contacts, through: :relationships
end
用于测试:使用 factory_girl我想创建一个能够成功创建 contact
记录的 contact
工厂。由于每个 contact
记录都需要关联的 contacts_team
记录和 relationship
记录:当我创建 contact
记录时,应该创建那些也是如此。同样:contacts_team
记录应具有与其关联的现有team
,而relation
记录应具有现有location
代码 > 它关联到。因此本质上它还应该创建一个位置
和一个团队
记录。
如何使用工厂创建联系人记录,从而实际上创建关联的 contacts_team
记录和 relationship
记录?
这是我目前的工厂:
FactoryGirl.define do
factory :contact do
first_name "Homer"
last_name "Simpson"
title "Nuclear Saftey Inspector"
end
end
FactoryGirl.define do
factory :contacts_team do
end
end
FactoryGirl.define do
factory :team do
name "Safety Inspection Team"
end
end
FactoryGirl.define do
factory :relationship do
end
end
FactoryGirl.define do
factory :location do
name "Safety Location"
end
end
如果使用factory_girl很难/不可能做到这一点:我该如何使用直接rspec来做到这一点?问题是我无法创建 contacts_team
记录或 relationship
记录,因为它关联的 contact
尚不存在!而且我无法创建 contact
记录,因为关联的 contacts_team
记录或 relationship
记录尚不存在。看起来我被困住了,但必须有一种不马虎的方法来做到这一点。
最佳答案
我上周刚刚有类似的要求。
在你的工厂结束后,你可以调用下一个工厂,然后它们就会关联起来。例如:
/spec/factories/contacts.rb
FactoryGirl.define do
factory :contact do |c|
first_name "Homer"
last_name "Simpson"
title "Nuclear Saftey Inspector"
# now, call the other two factories
relationship
contacts_team
end
factory :contacts_team do
# call the team factory
team
end
factory :relationship do
# call the location factory
location
end
# define the team and location factories...
end
现在,在/spec/controllers/contacts_controller_spec.rb
contact = FactoryGirl.create(:contact)
您可以使用 Factory Girl 来创建联系人,即使您只需要一个位置,因为所有内容都会立即生成。
替代方案(rspec)
不要“链接”你的工厂,而是在/spec/controllers/contacts_controller_spec.rb中
contact = FactoryGirl.create(:contact)
# use .create_list(model, number, parent) to make children of a specific parent
contacts_team = FactoryGirl.create_list(:contacts_team, 3, :contact => contact)
relationship = FactoryGirl.create_list(:relationship, 3, :contact => contact)
team = FactoryGirl.create_list(:team, 3, :contacts_team => contacts_team)
location = FactoryGirl.create_list(:location, 3, :relationship => relationship)
这将创建一个联系人,其中包含 3 个 contact_teams(包含 3 个团队)和 3 个关系(包含 3 个位置)
希望这可以帮助您找出正确的模式来制作测试数据:)
关于ruby-on-rails - FactoryGirl 和 RSpec : create a record with required nested_attributes for specs,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36207578/