validar validaciones rails polimorficas formulario asociaciones ruby-on-rails associations has-and-belongs-to-many factory-bot

ruby-on-rails - polimorficas - validaciones rails



Cómo crear has_and_belongs_to_many asociaciones en Factory girl (10)

Actualización para Rails 5:

En lugar de usar has_and_belongs_to_many association, debe considerar: has_many :through association.

La fábrica del usuario para esta asociación se ve así:

FactoryBot.define do factory :user do # user attributes factory :user_with_companies do transient do companies_count 10 # default number end after(:create) do |user, evaluator| create_list(:companies, evaluator.companies_count, user: user) end end end end

Puede crear la fábrica de la compañía de forma similar.

Una vez que ambas fábricas estén configuradas, puede crear la fábrica user_with_companies con la companies_count option . Aquí puede especificar a cuántas empresas pertenece el usuario: create(:user_with_companies, companies_count: 15)

Puede encontrar una explicación detallada acerca de las asociaciones de chicas de fábrica aquí .

Dado el siguiente

class User < ActiveRecord::Base has_and_belongs_to_many :companies end class Company < ActiveRecord::Base has_and_belongs_to_many :users end

¿cómo se definen las fábricas para empresas y usuarios, incluida la asociación bidireccional? Aquí está mi intento

Factory.define :company do |f| f.users{ |users| [users.association :company]} end Factory.define :user do |f| f.companies{ |companies| [companies.association :user]} end

ahora intento

Factory :user

Tal vez, como era de esperar, esto da como resultado un ciclo infinito, ya que las fábricas se usan recursivamente para definirse a sí mismas.

Más sorprendentemente, no he encontrado una mención de cómo hacer esto en ninguna parte, ¿hay un patrón para definir las fábricas necesarias o estoy haciendo algo fundamentalmente erróneo?


Antes que nada, te recomiendo usar has_many: through en lugar de habtm (más sobre esto here ), así que terminarás con algo como:

Employment belongs_to :users Employment belongs_to :companies User has_many :employments User has_many :companies, :through => :employments Company has_many :employments Company has_many :users, :through => :employments

Después de esto tendrás has_many association en ambos lados y puedes asignarlos en factory_girl de la manera en que lo hiciste.


Aquí está la solución que funciona para mí.

FactoryGirl.define do factory :company do #company attributes end factory :user do companies {[FactoryGirl.create(:company)]} #user attributes end end

si necesita una compañía específica, puede usar la fábrica de esta manera

company = FactoryGirl.create(:company, #{company attributes}) user = FactoryGirl.create(:user, :companies => [company])

Espero que esto sea útil para alguien.


En mi opinión, solo crea dos fábricas diferentes como:

Factory.define :user, :class => User do |u| # Just normal attributes initialization end Factory.define :company, :class => Company do |u| # Just normal attributes initialization end

Cuando escribe los casos de prueba para el usuario, simplemente escriba así

Factory(:user, :companies => [Factory(:company)])

Espero que funcione


Encontrado de esta manera agradable y detallado:

FactoryGirl.define do factory :foo do name "Foo" end factory :bar do name "Bar" foos { |a| [a.association(:foo)] } end end



Lo que funcionó para mí fue establecer la asociación cuando usé la fábrica. Usando tu ejemplo:

user = Factory(:user) company = Factory(:company) company.users << user company.save!


No pude encontrar un ejemplo para el caso mencionado anteriormente en el sitio web proporcionado. (Solo 1: N y asociaciones polimórficas, pero no habtm). Tuve un caso similar y mi código se ve así:

Factory.define :user do |user| user.name "Foo Bar" user.after_create { |u| Factory(:company, :users => [u]) } end Factory.define :company do |c| c.name "Acme" end


Puede definir una fábrica nueva y usar después de (: crear) una devolución de llamada para crear una lista de asociaciones. Veamos cómo hacerlo en este ejemplo:

FactoryBot.define do # user factory without associated companies factory :user do # user attributes factory :user_with_companies do transient do companies_count 10 end after(:create) do |user, evaluator| create_list(:companies, evaluator.companies_count, user: user) end end end end

Attribute companies_count es transitorio y está disponible en los atributos de la fábrica y en la devolución de llamada a través del evaluador. Ahora puede crear un usuario con empresas con la opción de especificar cuántas empresas desea:

create(:user_with_companies).companies.length # 10 create(:user_with_companies, companies_count: 15).companies.length # 15


factory :company_with_users, parent: :company do ignore do users_count 20 end after_create do |company, evaluator| FactoryGirl.create_list(:user, evaluator.users_count, users: [user]) end end

Advertencia: Cambiar usuarios: [usuario] a: usuarios => [usuario] para ruby ​​1.8.x.