Elixir错误处理管道选项

时间:2017-05-16 22:24:59

标签: error-handling elixir

以下代码是一个无效的变更集,但是由于错误消息最初未被匹配和记录,因此我花了很长时间才找到原因。

我在管道的末尾添加了一个case语句,这是拾取管道错误的最佳方法吗?

    User.changeset(%User{}, %{username: "username_is_test", password: "test", password_confirmation: "test", email: "test@test.com"})
    |> Repo.insert
    |> case  do
        {:ok, result} -> IO.puts("result")
        {:error, error} -> IO.inspect error
    end

2 个答案:

答案 0 :(得分:2)

管道和错误元组不能很好地协同工作。您可以使用case处理管道末尾的错误,但它仅适用于最后阶段。

对于返回错误元组的操作,我更喜欢使用with / else语法:

with changeset <- User.changeset(%User{}, %{username: "username_is_test", password: "test", password_confirmation: "test", email: "test@test.com"})
     {:ok, result} <- Repo.insert(changeset) do
  IO.puts("result")
else
  {:error, error} -> IO.inspect error
end

您可以根据with块中的要求添加尽可能多的可操作操作,并在else块中处理模式匹配的所有错误情况。

https://hexdocs.pm/elixir/Kernel.SpecialForms.html#with/1

答案 1 :(得分:2)

你有几个选择。如果您不想显式处理错误条件,则应使用Repo.insert!。如果变更集无效,至少会引发异常。

否则,您应该通过检查模板中的{:error, changeset}来使用处理changeset.action的案例句柄。

在更复杂的可能出错的管道中,我已经开始使用with特殊表格了。

with result when not is_nil(result) <- fun1, 
     {:ok, result} <- fun2(result), 
     {:ok, result} <- fun3(result) do
  success_handling(result)
else
  nil -> # handle first failure
  {:error, error} -> # handle other errors
  _ -> # catch all failure
end