View Source PipeHelpers (PipeHelpers v1.5.1)
Helpers for piping data. The provided helpers can be grouped into two categories:
- generate tuples that fit the return type of the containing function
- deal with previous function tuple output without "breaking the pipe"
1-return-tuples-builders
1. Return tuples builders
You can use only the first category to improve readability in your code.
For instance, lets take a typical Phoenix.LiveView
code:
def mount(_params, _session, socket) do
socket = assign(socket, my_bool_assign: true)
{:ok, socket}
end
With ok/1
, it can be rewritten as:
def mount(_params, _session, socket) do
socket
|> assign( my_bool_assign: true)
|> ok()
end
In addition to the typical {:ok, value}
return tuple, the library provides
the most common return types helpers noreply/1
reply/2
. Generic helpers
are also provided to build whatever tuple you need with pair/2
and rpair/2
.
2-tuple-deconstructors
2. Tuple deconstructors
In some situations, return type incompatibilities prevent you from using an uninterrupted pipe sequence. In this case, the following helpers may help:
2a-generic-unpair
2a Generic unpair
The generic unpair/1
allows you to ignore the first element of the pair
and forward the second for further piping.
2b-only-when-ok-execution
2b Only when "ok" execution
The then_ok/2
provides a promise-like solution to handle 'maybe ok'
results. If the result is an ok-tuple, it executes the function on the second argument
and passes the result forward (i.e. for further piping). If the result is not an
ok-tuple (typically an {:error, message}
tuple), it is forwarded directly.
For example, let's take the following (very powerful translator) function:
def translate(source) do
case source do
"ola" -> {:ok, "hello"}
_ -> {:error, "can't translate, sorry"}
end
end
And the quoting function that you want to pipe into:
def quote(text) do
text
end
The translate/1
output doesn't fit the quote/1
input, so the
following pipe is not possible:
my_source
|> translate()
|> quote()
With the then_ok/2
you can handle do:
my_source
|> translate()
|> then_ok("e/1)
This pipe will either return the properly quoted translation or the error tuple
generated by the translate/1
.
If you intend to successively pipe into more than a single functions after an
{:ok, result}
returning function, you need to only have{:ok, result}
functions except the last one and always use thethen_ok/2
construct until the end. Doing so you can safely do the error management at the end of the pipe using a|> case do
irrespective of the function that failed to provide an{:ok, result}
output.
The then_on/3
provides similar behaviour with a more generic/powerful pattern
matching on the previous function output.
The functions above have their tap
counterpart if the idea is to apply a
conditional side effect without modifying the piped value.
Link to this section Summary
Functions
Wrap into {:cont, state}
tuple (phoenix socket format).
Wrap into standard {:error, result}
tuple.
Wrap into {:halt, state}
tuple (phoenix socket format).
Wrap into {:halt, reply, state}
tuple (phoenix socket format).
Wrap into {:noreply, state}
tuple (genserver and phoenix socket format).
Wrap into standard {:ok, result}
tuple.
If result
is an error tuple, execute fun
with the right part of result
tuple as single argument
and return fun
output.
Otherwise, return result
as-is.
Wrap into generic tuple pair.
Wrap into {:reply, reply, state}
tuple (genserver and phoenix socket format).
Wrap into tuple rpair.
Wrap into {:reply, reply, state}
tuple (genserver and phoenix socket format).
Execute fun
function only if result
is an ok-tuple. Returns the input in any case.
Execute fun
function only if the first arument matches the second one (value = result
check).
Returns the input in any case.
Then only if condition is true.
If result
is an ok tuple, execute fun
with the right part of result
tuple as single argument
and return fun
output.
Otherwise, return result
as-is.
Then only if value match. See then_ok/2
and tap_ok/3
Unwrap from a tuple pair.
Unwrap a tuple, but raise if not {:ok, value}
Link to this section Functions
Wrap into {:cont, state}
tuple (phoenix socket format).
Wrap into standard {:error, result}
tuple.
example
Example
iex> :not_found |> err()
{:error, :not_found}
Wrap into {:halt, state}
tuple (phoenix socket format).
Wrap into {:halt, reply, state}
tuple (phoenix socket format).
Wrap into {:noreply, state}
tuple (genserver and phoenix socket format).
example
Example
iex> state = "gen server state"
...> state |> noreply()
{:noreply, "gen server state"}
Wrap into standard {:ok, result}
tuple.
example
Example
iex> socket = "socket"
...> socket |> ok()
{:ok, "socket"}
If result
is an error tuple, execute fun
with the right part of result
tuple as single argument
and return fun
output.
Otherwise, return result
as-is.
Wrap into generic tuple pair.
example
Example
iex> 1 |> pair(2)
{2, 1}
Wrap into {:reply, reply, state}
tuple (genserver and phoenix socket format).
example
Example
iex> state = "gen server state"
...> r = "reply"
...> state |> reply(r)
{:reply, "reply", "gen server state"}
Wrap into tuple rpair.
example
Example
iex> 1 |> rpair(2)
{1, 2}
Wrap into {:reply, reply, state}
tuple (genserver and phoenix socket format).
example
Example
iex> state = "gen server state"
...> r = "reply"
...> r |> rreply(state)
{:reply, "reply", "gen server state"}
Execute fun
function only if result
is an ok-tuple. Returns the input in any case.
The fun
argument is a function taking the right part of the ok-tuple
as an optional argument.
example
Example
iex> {:ok, "somedata"} |> tap_ok(fn -> "only executed when {:ok, ...}" end)
{:ok, "somedata"}
iex> {:error, "failed"} |> tap_ok(fn -> "not executed when not {:ok, ...}" end)
{:error, "failed"}
Execute fun
function only if the first arument matches the second one (value = result
check).
Returns the input in any case.
example
Example
iex> true |> tap_on(true, fn -> "only executed when matching 'true'" end)
true
iex> false |> tap_on(true, fn -> "not executed when not matchin 'true'" end)
false
Then only if condition is true.
If result
is an ok tuple, execute fun
with the right part of result
tuple as single argument
and return fun
output.
Otherwise, return result
as-is.
example
Example
iex> {:ok, "somedata"} |> then_ok(fn -> "only returned when result argument is {:ok, ...}" end)
"only returned when result argument is {:ok, ...}"
iex> {:error, "failed"} |> then_ok(fn -> "only returned when result argument is {:ok, ...}" end)
{:error, "failed"}
Then only if value match. See then_ok/2
and tap_ok/3
Unwrap from a tuple pair.
example
Example
iex> {:ok, 1} |> unpair()
1
Unwrap a tuple, but raise if not {:ok, value}
example
Example
iex> {:ok, "hello"} |> unwrap!()
"hello"