2016-05-07 6 views
3

Ich habe eine kleine Pipeline in Elixier, es geht um ecto Modellzustand zu ändern:Elixir - wie Conditional Pipe in die Pipeline hinzufügen?

model 
|> cast(params, ~w(something), ~w()) 
|> conditional 
|> Repo.update 

Das Problem ist, dass ich conditional Rohr, das Null manchmal sein kann, so dass in dem Fall gleich Null, es ist es nichts tun soll, und kann funktioniert (ich nehme an, es wird fn(x) -> x end)

Also ist meine Frage: "Wie kann ich das tun"?

+0

Also ist 'conditional' entweder eine Funktion oder keine? – Dogbert

+0

Ja !!!!!!!!!!!! – asiniy

Antwort

11
model 
|> cast(params, ~w(something), ~w()) 
|> maybe_do_something(conditional) 
|> Repo.update 

defp maybe_do_something(changeset, nil), do: changeset 

defp maybe_do_something(changeset, func) do 
    # Do something with changeset 
end 

Nicht sicher, ob ich Ihre Frage richtig beantwortet habe, aber vielleicht ist das, was Sie suchen.

5

Rohre sind ideal für Operationen, die nicht fehlschlagen können und alle von ihnen werden immer getragen werden. Falls Sie die Pipeline stoppen möchten, können Sie dies nicht tun. Sie müssten Funktionen schreiben, wie folgt aus:

maybe_repo_update(nil), do: nil 
maybe_repo_update(data), do: Repo.update(data) 

Um dieses Problem zu lösen, gibt es eine neue spezielle Form in Elixir 1.2 with genannt wird. Es kann im Moment um die Pipeline zu stoppen, wo etwas nicht mit:

with changeset <- cast(model, params, ~w(something), ~w()) 
    {:ok, changeset} <- conditional_operation(changeset) 
    {:ok, model} <- Repo.insert(changeset) 

Dadurch wird sichergestellt, dass, wenn bedingte Operation etwas anderes als {:ok, changeset} zurück wird es nicht versuchen, den letzten Repo-Einsatz laufen. In Elixir 1.3 können Sie auch else Teil verwenden.

jedoch für Changesets ist es häufiger Lösung von @JustMichael vorgeschlagen zu verwenden:

def conditional(changeset) do 
    if something_to_do do 
    transform(changeset) 
    else 
    changeset 
    end 
end 

Diese Lösung wird den Repo.update Teil immer laufen.

0

Ich bin Elixir Neuling, also bitte nicht zu hart :).

Warum nicht anonyme Funktionen für diesen Zweck verwenden?

model 
|> cast(params, ~w(something), ~w()) 
|> (fn(n) -> conditional && n |> Repo.update || n end).()