我有一个工厂,产生有一项用户W上的发动机内/角色。用户模型has_many :roles through: :roles_users
。我能得到的代码与after(:create)
条款而与association:
关键字工作。
这工作:
应用程序/模型/ myengine / role.rb
module MyEngine
class User < ActiveRecord::Base
has_many :roles_users
has_many :roles, through: :roles_users
end
end
规格/工厂/ roles.rb
factory :role, class: "MyEngine::Role" do
type: { 'admin' }
end
factory :user, class: "MyEngine::User" do
sequence(:email) { |n| "tester_#{n}@example.com" }
password { 'xxx' }
password_confirmation { 'xxx' }
after(:create) do |user|
user.roles << FactoryBot.create(:role)
end
end
但这并不和测试失败,undefined method 'each' for #<MyEngine::Role:0x0...>
在初始化:
factory :user, class: "MyEngine::User" do
sequence(:email) { |n| "tester_#{n}@example.com" }
password { 'xxx'}
password_confirmation { 'xxx' }
association: :roles, factory: :role
end
更新/编辑如下:
该FactoryBot文档只建议后(:创建)挂钩可能是有原因的。从用户的意见有两个问题与上面的代码:
使用角色协会可以直接使用集合,而不是一个对象被分配@Vasfed的建议:
factory :user, class: "MyEngine::User" do
sequence(:email) { |n| "tester_#{n}@example.com" }
password { 'xxx'}
password_confirmation { 'xxx' }
roles { [ create(:role) ] }
end
按照@ulferts建议,使用新的,而不是创造:
factory :user, class: "MyEngine::User" do
sequence(:email) { |n| "tester_#{n}@example.com" }
password { 'xxx'}
password_confirmation { 'xxx' }
roles { [ build(:role) ] }
end
双方将产生:
ActiveRecord::RecordInvalid: Validation failed: Roles users is invalid
由于该模型没有验证,这似乎指向麻烦瓦特/缺少的FK表记录或无法找到FK表,可能是由于命名空间分辨率。
这个错误是因为你在角色传递单个实例roles
而不是收藏。 FactoryBot没有办法知道你要多少角色创建关联的方式,所以需要手动创建反正。
简单的解决方法无后钩可roles { [ create(:role) ] }