Defer job ignore to GenServer init

This commit is contained in:
Andrew Dryga
2024-04-18 17:05:23 -06:00
parent 89dd4c5a72
commit 1b1b44dcaa
3 changed files with 31 additions and 28 deletions

View File

@@ -28,10 +28,14 @@ defmodule Domain.Jobs.Executors.Concurrent do
@impl true
def init({module, interval, config}) do
initial_delay = Keyword.get(config, :initial_delay, 0)
if Keyword.get(config, :enabled, true) do
initial_delay = Keyword.get(config, :initial_delay, 0)
with {:ok, worker_state} <- module.state(config) do
{:ok, {module, worker_state, interval}, initial_delay}
with {:ok, worker_state} <- module.state(config) do
{:ok, {module, worker_state, interval}, initial_delay}
end
else
:ignore
end
end

View File

@@ -61,27 +61,31 @@ defmodule Domain.Jobs.Executors.GloballyUnique do
@impl true
def init({module, interval, config}) do
name = global_name(module)
if Keyword.get(config, :enabled, true) do
name = global_name(module)
# `random_notify_name` is used to avoid name conflicts in a cluster during deployments and
# network splits, it randomly selects one of the duplicate pids for registration,
# and sends the message {global_name_conflict, Name} to the other pid so that they stop
# trying to claim job queue leadership.
with :no <- :global.register_name(name, self(), &:global.random_notify_name/3),
pid when is_pid(pid) <- :global.whereis_name(name) do
# we monitor the leader process so that we start a race to become a new leader when it's down
monitor_ref = Process.monitor(pid)
{:ok, {{module, interval, config}, {:fallback, pid, monitor_ref}}, :hibernate}
# `random_notify_name` is used to avoid name conflicts in a cluster during deployments and
# network splits, it randomly selects one of the duplicate pids for registration,
# and sends the message {global_name_conflict, Name} to the other pid so that they stop
# trying to claim job queue leadership.
with :no <- :global.register_name(name, self(), &:global.random_notify_name/3),
pid when is_pid(pid) <- :global.whereis_name(name) do
# we monitor the leader process so that we start a race to become a new leader when it's down
monitor_ref = Process.monitor(pid)
{:ok, {{module, interval, config}, {:fallback, pid, monitor_ref}}, :hibernate}
else
:yes ->
Logger.debug("Recurrent job will be handled on this node", module: module)
initial_delay = Keyword.get(config, :initial_delay, 0)
{:ok, {{module, interval, config}, :leader}, initial_delay}
:undefined ->
Logger.warning("Recurrent job leader exists but is not yet available", module: module)
_timer_ref = :timer.sleep(100)
init(module)
end
else
:yes ->
Logger.debug("Recurrent job will be handled on this node", module: module)
initial_delay = Keyword.get(config, :initial_delay, 0)
{:ok, {{module, interval, config}, :leader}, initial_delay}
:undefined ->
Logger.warning("Recurrent job leader exists but is not yet available", module: module)
_timer_ref = :timer.sleep(100)
init(module)
:ignore
end
end

View File

@@ -9,12 +9,7 @@ defmodule Domain.Jobs.Job do
def child_spec(_opts) do
config = __config__()
if Keyword.get(config, :enabled, true) do
Supervisor.child_spec({@executor, {__MODULE__, @interval, config}}, id: __MODULE__)
else
:ignore
end
Supervisor.child_spec({@executor, {__MODULE__, @interval, config}}, id: __MODULE__)
end
@doc """