创建嵌套关联

问题描述

请考虑以下架构:

schema "businesses" do
  ...
  has_many :contacts,Contact
  has_many :conversations,Conversation
  ...
end
schema "contacts" do
  ...
  belongs_to :business,Business
  has_one :conversation,Conversation
  ...
end
schema "conversations" do
  ...
  belongs_to :business,Business
  belongs_to :contact,Contact
  has_many :messages,Message
  ...
end
schema "messages" do
  belongs_to :conversation,Conversation
  belongs_to :contact,Contact
end

This answer显示了如何将两个关联放在一个结构上。

我遵循了这种模式,效果很好。

def create_conversation(%{business: business,contact: contact,message: message} = attrs) do
  business
  |> Ecto.build_assoc(:conversations)
  |> Ecto.Changeset.change()
  |> Ecto.Changeset.put_assoc(:contact,contact)
  |> Repo.insert()
end

但是,我想知道如何同时创建一个message(它是上面新创建的conversation的关联)的惯用方式吗? conversation。一次Repo.insert()调用是否这样做有意义?在Elixir / Ecto中有经验的人将如何解决这个问题?

解决方法

哇,这行得通!

def create_conversation(%{business: business,contact: contact,message: message} = attrs) do
  business
  |> Ecto.build_assoc(:conversations)
  |> Ecto.Changeset.change()
  |> Ecto.Changeset.put_assoc(:contact,contact)
  |> Ecto.Changeset.put_assoc(:messages,[%Message{body: message.body}])
  |> Repo.insert()
end