Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save Fire-Dragon-DoL/07fcb687ef644a521680dcc8aa26cf14 to your computer and use it in GitHub Desktop.
Save Fire-Dragon-DoL/07fcb687ef644a521680dcc8aa26cf14 to your computer and use it in GitHub Desktop.
Delegate all functions to another module, with pattern match on first argument
defmodule LikeMapModule do
defstruct [data: %{}]
# Delegates all functions of Map to Map, with first argument `data`
for {fun, arity} <- Map.__info__(:functions), arity > 0 do
args =
arity
|> Macro.generate_arguments(__MODULE__)
|> Enum.with_index()
|> Enum.map(fn {arg, idx} ->
case idx do
0 ->
quote do
%unquote(__MODULE__){} = unquote(arg)
end
_ ->
arg
end
end)
def unquote(fun)(unquote_splicing(args)) do
[arg1 | rest] = unquote(args)
args = [arg1.data | rest]
result = Kernel.apply(Map, unquote(fun), args)
# XXX: This creates problem in case of functions not returning the struct itself
# the snippet can probably be updated to address it
%{arg1 | data: result}
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment