Gezien het volgende
class User < ActiveRecord::Base
has_and_belongs_to_many :companies
end
class Company < ActiveRecord::Base
has_and_belongs_to_many :users
end
hoe definieer je fabrieken voor bedrijven en gebruikers, inclusief de bidirectionele associatie? Hier is mijn poging
Factory.define :company do |f|
f.users{ |users| [users.association :company]}
end
Factory.define :user do |f|
f.companies{ |companies| [companies.association :user]}
end
nu probeer ik
Factory :user
Het is misschien niet verwonderlijk dat dit resulteert in een oneindige lus, aangezien de fabrieken elkaar recursief gebruiken om zichzelf te definiëren.
Verrassenderwijs heb ik nergens vermeld hoe ik dit moet doen, is er een patroon voor het definiëren van de noodzakelijke fabrieken of doe ik iets fundamenteel verkeerd?
Antwoord 1, autoriteit 100%
Hier is de oplossing die voor mij werkt.
FactoryGirl.define do
factory :company do
#company attributes
end
factory :user do
companies {[FactoryGirl.create(:company)]}
#user attributes
end
end
als u een specifiek bedrijf nodig heeft, kunt u de fabriek op deze manier gebruiken
company = FactoryGirl.create(:company, #{company attributes})
user = FactoryGirl.create(:user, :companies => [company])
Ik hoop dat dit iemand kan helpen.
Antwoord 2, autoriteit 30%
Factorygirl is sindsdien bijgewerkt en bevat nu callbacks om dit probleem op te lossen. Kijk eens op http://robots.thoughtbot.com/post /254496652/aint-no-calla-back-girlvoor meer info.
Antwoord 3, autoriteit 16%
Naar mijn mening, maak gewoon twee verschillende fabrieken zoals:
Fabriek.define :gebruiker, :class => Gebruiker doet |u| # Gewoon normale attributen initialisatie einde Fabriek.define :bedrijf, :class => Bedrijf doen |u| # Gewoon normale attributen initialisatie einde
Als je de testcases voor de gebruiker schrijft, schrijf dan gewoon zo
Fabriek(:gebruiker, :bedrijven => [Fabriek(:bedrijf)])
Hoop dat het werkt.
Antwoord 4, autoriteit 7%
Ik kon geen voorbeeld vinden voor het bovengenoemde geval op de aangeboden website. (Alleen 1:N en polymorfe associaties, maar geen habtm). Ik had een soortgelijk geval en mijn code ziet er als volgt uit:
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
Antwoord 5, autoriteit 4%
Wat voor mij werkte, was het instellen van de associatie bij het gebruik van de fabriek.
Uw voorbeeld gebruiken:
user = Factory(:user)
company = Factory(:company)
company.users << user
company.save!
Antwoord 6, autoriteit 3%
Zo leuk en uitgebreid gevonden:
FactoryGirl.define do
factory :foo do
name "Foo"
end
factory :bar do
name "Bar"
foos { |a| [a.association(:foo)] }
end
end
Antwoord 7, autoriteit 2%
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
Waarschuwing:wijzig gebruikers: [gebruiker] in :users => [gebruiker] voor ruby 1.8.x
Antwoord 8
Voor HABTM heb ik eigenschappen en callbacks gebruikt.
Stel dat je de volgende modellen hebt:
class Catalog < ApplicationRecord
has_and_belongs_to_many :courses
…
end
class Course < ApplicationRecord
…
end
U kunt bepalen de Factory boven
FactoryBot.define do
factory :catalog do
description "Catalog description"
…
trait :with_courses do
after :create do |catalog|
courses = FactoryBot.create_list :course, 2
catalog.courses << courses
catalog.save
end
end
end
end
Antwoord 9
Allereerst wil ik u ten zeerste aan gebruik has_many: door middel van in plaats van HABTM (meer over dit hier ), dus je zult eindigen met iets als:
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
Hierna kun has_many vereniging aan beide zijden zult hebben en kan in factory_girl toe te kennen in de manier waarop je het deed.
Antwoord 10
Update voor Rails 5:
In plaats van has_and_belongs_to_many
vereniging, u zou moeten overwegen: has_many :through
vereniging
De gebruiker fabriek voor deze vereniging ziet er als volgt uit:
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
U kan het bedrijf de fabriek te creëren op een vergelijkbare manier.
Zodra beide fabrieken zijn ingesteld, u kunt maken user_with_companies
fabriek met companies_count option
. Hier kunt u opgeven hoe veel bedrijven de gebruiker behoort: create(:user_with_companies, companies_count: 15)
U kunt gedetailleerde uitleg over fabriek meisje verenigingen vinden hier .
Antwoord 11
U kunt nieuwe fabriek en het gebruik opgeven na (: te maken) callback om een lijst van de verenigingen te creëren. Laten we eens kijken hoe dat te doen in dit voorbeeld:
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
Kenmerk companies_count is een tijdelijke en verkrijgbaar in attributen van de fabriek en in de callback via de beoordelaar. Nu kun je een gebruiker met bedrijven te maken met de mogelijkheid om aan te geven hoeveel bedrijven je wilt:
create(:user_with_companies).companies.length # 10
create(:user_with_companies, companies_count: 15).companies.length # 15