Packages

Toolbox that help to do trivial things faster. I have more free time for life

Current section

Files

Jump to
magik lib maybe.ex
Raw

lib/maybe.ex

defmodule Magik.Maybe do
@moduledoc """
This module provides helpers method to call function depend on condition
"""
@doc """
This helper is used in pipe, to invoke function if condition is true, otherwise passing data to nex function
**Example**
a = 10
b = 12
a
|> Kernel.*(2)
|> Maybe.pipe( b != 0, & &1/b)
|> Kernel.+(10)
**The condition**
Could be any value:
- if condition is `true` then call the function with the first argument
- if condition is `function/1` then invoke condition function. If return value is `true` then invoke the function with first argument
- other value of condition don't trigger the function and just return the first argument that passed to this function
**Example 2**
Using function condition
a = 10
a
|> Kernel.+(3)
|> Maybe.pipe(& &1 > 0, & &1 - 5)
"""
@spec pipe(any, condition :: any, function) :: any
def pipe(data, true, func) when is_function(func, 1) do
func.(data)
end
def pipe(data, guard_func, func) when is_function(func, 1) and is_function(guard_func, 1) do
if guard_func.(data) do
func.(data)
else
data
end
end
def pipe(data, _, _), do: data
@doc """
This function check first argument, if it is tuple of `{:ok, data}` then invoke the function with `data` of the tuple. Otherwise return the first argument.
**Example**
changeset = User.changeset(%User{}, params)
Repo.insert(changeset)
|> Maybe.pipe(fn user ->
# do something with user
end)
In case you are using `with`, don't care about this function
"""
@spec pipe({:ok, any} | any, function) :: any
def pipe({:ok, data}, func) when is_function(func, 1) do
func.(data)
end
def pipe(data, _), do: data
@doc """
This function is mostly used with `with`. In some case, you may want to invoke a function if it meets a specific condition without breaking `with` into 2 block like this
params = %{}
with {:ok, data} <- insert_something(),
:ok <- (if params.checked, do: do_something(data), else: :ok),
{:ok, another_data} <- send_something(data) do
# aha
end
This function help to write it shorter
params = %{}
with {:ok, data} <- insert_something(),
:ok <- Maybe.run(params.checked, &do_something(data)),
{:ok, another_data} <- send_something(data) do
# aha
end
"""
def run(nil, _func), do: :ok
def run(false, _func), do: :ok
def run(true, func) when is_function(func) do
func.()
end
def ok?({:error, _}), do: false
def ok?(_), do: true
def error?({:error, _}), do: true
def error?(_), do: false
end