无法使用 FactoryBot 在 Rspec 中建立 has_and_belongs_to_many 关系

Unable to build has_and_belongs_to_many relation in Rspec with FactoryBot

我在这里阅读了 FactoryBot 的文档:https://www.rubydoc.info/gems/factory_bot/file/GETTING_STARTED.md

我有用户和角色,这是一个 has_and_belongs_to_many 关系。我已经尝试了文档中的许多步骤来设置这种关系,但没有任何效果。

首先,我尝试了这个技巧:

FactoryBot.define do
  factory :role do
    name { "marketing" }

    factory :admin_role do
      name { "admin" }
    end
  end
end

FactoryBot.define do
  factory :user, aliases: [:marketing] do
    email { 'marketing@mysite.io' }
    password { '123456' }
    password_confirmation { '123456' }
    association :role
  end
end

但它给了我:

NoMethodError: undefined method `role=' for #<User:0x007f9743449198>

其次,我尝试了这个技巧:

FactoryBot.define do
  factory :role do
    name { "marketing" }

    factory :admin_role do
      name { "admin" }
    end
  end
end

FactoryBot.define do
  factory :user, aliases: [:marketing] do
    email { 'marketing@mysite.io' }
    password { '123456' }
    password_confirmation { '123456' }
    role
  end
end

但我再次收到此错误:

NoMethodError: undefined method `role=' for #<User:0x007f9743449198>

第三,我尝试了这种复数关系的技巧:

FactoryBot.define do
  factory :role do
    name { "marketing" }

    factory :admin_role do
      name { "admin" }
    end
  end
end

FactoryBot.define do
  factory :user, aliases: [:marketing] do
    email { 'marketing@mysite.io' }
    password { '123456' }
    password_confirmation { '123456' }
    role
  end
end

我收到这个错误:

ArgumentError: Trait not registered: roles

然而,当我阅读文档时,它建议我可以使用这些方法。那我做错了什么?

不确定这是否可行,但由于用户可以拥有多个角色,您可能需要将角色添加为单个数组项

FactoryBot.define do
  factory :user, aliases: [:marketing] do
    email { 'marketing@mysite.io' }
    password { '123456' }
    password_confirmation { '123456' }
    roles { [ role ] }
  end
end

或者

FactoryBot.define do
  factory :user, aliases: [:marketing] do
    email { 'marketing@mysite.io' }
    password { '123456' }
    password_confirmation { '123456' }
    roles { [ create(role) ] }
  end
end

你的错误原因是你不能调用 @user.role 但你可以用 HABTM 关系调用 @user.roles