Current section

Files

Jump to
double_down lib double_down contract dispatch defer.ex
Raw

lib/double_down/contract/dispatch/defer.ex

defmodule DoubleDown.Contract.Dispatch.Defer do
@moduledoc """
A deferred execution marker.
When a handler or test double returns `%DoubleDown.Contract.Dispatch.Defer{fun: fun}`,
the dispatch system releases the NimbleOwnership lock before calling
`fun.()`. This avoids deadlocks when the deferred function makes
further dispatched calls (e.g. `transact` calling `insert` inside
its body).
**For users of the Double API**, prefer `DoubleDown.Double.defer/1`
over constructing this struct directly.
Used internally by `Repo.Stub`, `Repo.OpenInMemory`, and
`DoubleDown.Double`'s canonical handler.
"""
@enforce_keys [:fun]
defstruct [:fun]
@type t :: %__MODULE__{fun: (-> term())}
@doc "Create a new Defer marker. Validates that `fun` is a 0-arity function."
@spec new((-> term())) :: t()
def new(fun) when is_function(fun, 0), do: %__MODULE__{fun: fun}
end