defmodule GenConsumer do @moduledoc """ Documentation for GenConsumer. ## Usage defmodule MyApp.EventHandler do use GenConsumer, otp_app: :my_app @impl true def handle(event, state) do {:ok, state} end end """ @doc false defmacro __using__(opts) do quote bind_quoted: [opts: opts] do use GenServer alias GenConsumer.Serdes def __adapter__, do: GenConsumer.Config.compile_config(__MODULE__, opts) def child_spec(opts) do %{ id: __MODULE__, start: {__MODULE__, :start_link, [opts]}, type: :worker } end def start_link(opts \\ []) do opts = Keyword.merge(__adapter__().opts, opts) name = Keyword.get(opts, :name, __MODULE__) GenServer.start_link(__MODULE__, opts, name: name) end def init(start_opts) do callback = fn event -> event = Serdes.decode(event) __MODULE__.handle_event(event) end opts = start_opts |> Keyword.merge(__adapter__().opts) |> Keyword.put(:callback, callback) __adapter__().module.init(opts) end def handle_info(event, state) do __adapter__().module.handle_info(event, state) end def handle_event(_) do :ok end defoverridable handle_event: 1 end end end