View Source PipeHelpers (PipeHelpers v1.5.1)

Helpers for piping data. The provided helpers can be grouped into two categories:

  1. generate tuples that fit the return type of the containing function
  2. 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(&quote/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 the then_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"}
Link to this function

tap_on(result, value, fun)

View Source

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
Link to this function

then_if(value, arg2, fun)

View Source

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"}
Link to this function

then_on(value, value, fun)

View Source

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"