ruby-on-rails - rails - rspec factory bot
Factory Girl: ¿Cómo asociar un registro a otro registro sin crear un nuevo registro? (3)
Estoy usando Factory Girl / Rspec2 / Rails 3.
En factories.rb , tengo:
Factory.define :user do |user|
user.name ''Some guy''
user.email ''[email protected]''
user.password ''password''
end
Factory.define :org_admin, :parent => :user do |user|
user.email ''[email protected]''
end
Factory.define :user_with_membership_request, :parent => :user do |user|
user.email ''[email protected]''
end
Factory.define :organization do |org|
org.name ''MEC''
org.description ''Mountain Equipment Co-op''
end
Factory.define :membership do |membership|
membership.user { Factory(:user) }
membership.organization { Factory(:organization) }
end
Factory.define :admin_membership, :parent => :membership do |membership|
membership.user { Factory(:org_admin) }
membership.is_admin true
membership.status ''active''
end
Factory.define :membership_request, :parent => :membership do |membership|
membership.user { Factory(:user_with_membership_request) }
membership.status ''requested''
end
y luego en mi prueba rspec tengo:
it ''should accept the membership request'' do
@org_admin = Factory(:org_admin)
test_sign_in(@org_admin)
@organization = Factory(:organization)
@membership_request = Factory(:membership_request)
put :update, :organization_id => @organization.id, :id => @membership_request.id, :acceptance => ''approve''
...
end
Cuando ejecuto la prueba, me sale:
Failure/Error: @membership_request = Factory(:membership_request)
Validation failed: Name has already been taken
Entiendo que la razón de la falla es porque FactoryGirl está creando otra organización (con el mismo nombre).
Pero lo que me gustaría hacer es crear varias membresías asociadas con la misma organización. ¿Cómo puedo hacer eso?
Gracias.
Sean
Con mongoid puede combinar el uso del método #find_or_create_by con Factory.attributes_for y hacer algo como esto
factory :membership do
organization { Organization.find_or_create_by(Factory.attributes_for(:organization))}
end
Estoy seguro de que ActiveRecord tiene algo similar.
Hay dos cosas 1. Es posible que aún desee crear nombres únicos para Factory(:organisation)
que puede lograr usando Factory.sequence
que lo generará de forma exclusiva para usted. 2. Puede pasar una Factory(:membership_request, :organization => @organization)
para usar el objeto existente en lugar de crear uno nuevo.
Puede buscar una organización existente y usarla, o crear una si no existe:
Factory.define :membership do |membership|
membership.user { Factory(:user) }
membership.organization { Organization.first || Factory(:organization) }
end
FactoryGirl 4+ actualización:
Factory.define do
factory :membership do
user { create(:user) }
organization { Organization.first || create(:organization) }
end
end
Otro enfoque es utilizar identificadores únicos (por ejemplo, nombres) para cada fábrica que desee reutilizar, luego use initialize_with
para generarlo:
factory :organization_1 do
ignore { organization_name ''Sample Organization 1'' }
name { organization_name }
initialize_with { Organization.find_or_create_by_name(organization_name) }
end
Ahora cualquier referencia a :organization_1
siempre recuperará la misma Organization
. Obviamente, debes usar nombres distintos para que esto funcione.