我正在尝试插入发票结构及其关联的发票项目。我能够插入发票数据,并调用匿名函数来验证、转换和插入每个项目。由于 insert/2 不会产生退货,如果一个项目验证或插入失败,我如何获取项目的 invoice_id 同时仍然能够回滚整个交易?
我已经将代码放在我自己的仓库中,这里是:
def insertassoc(params) do
Repo.transaction(fn ->
i = Invoice.changeset(params["data"], :create)
if i.valid? do
Repo.insert(i)
else
Repo.rollback(i.errors)
end
insert_include = fn k ->
c = InvoiceItem.changeset(k, :create)
if c.valid? do
Repo.insert(c)
else
Repo.rollback(c.errors)
end
end
for include <- params["includes"] do
insert_include.(Map.merge(include, %{"invoice_id" => ????}))
end
end)
end
这是我从控制器中使用它的方式:
def create(conn, params) do
case InvoiceRepo.insertassoc(params) do
{:ok, x} ->
json conn, Map.merge(params, %{"message" => "OK"})
{:error, x} ->
json conn |> put_status(400), Map.merge(params, %{"message"
=> "Error"})
end
end
Ecto 的最新示例并不多,如果这些是菜鸟问题,请见谅 ;-)。有人有想法吗?我尝试将发票插入到一个私有函数中,并使用一个案例块来确定主事务是否应该回滚,但我也不知道如何从中获取发票 ID。