class Agents << ActiveRecord::Base
belongs_to :customer
belongs_to :house
end
class Customer << ActiveRecord::Base
has_many :agents
has_many :houses, through: :agents
end
class House << ActiveRecord::Base
has_many :agents
has_many :customers, through: :agents
end
Comment puis-je ajouter au modèle Agents
pour Customer
?
Est-ce le meilleur moyen?
Customer.find(1).agents.create(customer_id: 1, house_id: 1)
Ce qui précède fonctionne bien depuis la console, cependant, je ne sais pas comment y parvenir dans l’application réelle.
Imaginez un formulaire pour le client qui prend également house_id
comme entrée. Puis-je effectuer les opérations suivantes dans mon contrôleur?
def create
@customer = Customer.new(params[:customer])
@customer.agents.create(customer_id: @customer.id, house_id: params[:house_id])
@customer.save
end
Globalement, je suis confus quant à la façon d'ajouter des enregistrements dans le has_many :through
table?
Je pense que vous pouvez simplement faire ceci:
@cust = Customer.new(params[:customer])
@cust.houses << House.find(params[:house_id])
Ou lors de la création d'une nouvelle maison pour un client:
@cust = Customer.new(params[:customer])
@cust.houses.create(params[:house])
Vous pouvez également ajouter via les identifiants:
@cust.house_ids << House.find(params[:house_id])
Le "meilleur moyen" dépend de vos besoins et de ce qui vous semble le plus confortable. La confusion provient des différences de comportement d'ActiveRecord entre les méthodes new
et create
et le <<
_ opérateur.
new
new
n'ajoutera pas d'enregistrement d'association pour vous. Vous devez créer les enregistrements House
et Agent
:
house = @cust.houses.new(params[:house])
house.save
agent = Agent(customer_id: @cust.id, house_id: house.id)
agent.save
Notez que @cust.houses.new
et House.new
sont en fait les mêmes car vous devez créer l’enregistrement Agent
dans les deux cas.
<<
OpérateurComme le mentionne Mischa, vous pouvez également utiliser le <<
opérateur sur la collection. Ceci construira seulement le modèle Agent
pour vous, vous devez construire le modèle House
:
house = House.create(params[:house])
@cust.houses << house
agent = @cust.houses.find(house.id)
create
create
construira les enregistrements House
et Agent
pour vous, mais vous devrez trouver le modèle Agent
si vous souhaitez le renvoyer à votre vue ou api:
house = @cust.houses.create(params[:house])
agent = @cust.agents.where(house: house.id).first
Pour terminer, si vous souhaitez que des exceptions soient générées lors de la création de house
, utilisez plutôt les opérateurs bang (par exemple, new!
et create!
).
Une autre façon d’ajouter des associations consiste à utiliser les colonnes de clé étrangère:
agent = Agent.new(...)
agent.house = House.find(...)
agent.customer = Customer.find(...)
agent.save
Ou utilisez les noms de colonne exacts en passant l'ID de l'enregistrement associé à la place de l'enregistrement.
agent.house_id = house.id
agent.customer_id = customer.id