Супервайзер с Quantum Elixir Cron Job
Простите, если я не очень хорошо понимаю эликсир, так как я новичок в этом...
Я использую квантовый эликсир в качестве cron api для динамического создания заданий cron. Когда кто-то размещает на маршруте, я сохраняю детали задания cron в моем Ecto Repo, а затем одновременно создаю квантовое задание с Quantum.add_job
,
В процессе разработки, когда я закрываю свой сервер и перезапускаю его, мне нужно заново добавить все мои задания cron, потому что они не выживают после перезапуска. Это заставило меня задуматься о том, что если мое приложение будет аварийно завершено, это приведет к потере всех заданий cron. (Я имею в виду сценарии, в которых я размещаю приложение на вычислительном движке Google и по какой-либо причине необходимо выполнить сброс на экземпляре Compute, то есть выполнить обновление на коробке и т. Д.)
Так что мне было интересно, как правильно перезапустить мое приложение, сохранив эти задания cron?
Прямо сейчас у меня есть следующее:
worker(Task,[MyApp.RebootTask, :reboot, []], restart: :transient)
в start
функция моего модуля приложения.
Это правильный подход? Какие еще соображения мне нужно учитывать?
Любое руководство с благодарностью
1 ответ
Я запрашиваю свою базу данных и создаю список с определением задания для каждого элемента
%Quantum.Job{
name: job_name,
overlap: false,
run_strategy: %Quantum.RunStrategy.Random{nodes: :cluster},
schedule: Crontab.CronExpression.Parser.parse!(schedule),
task: task,
state: :active,
timezone: "Europe/Zurich"
}
Чтобы задания запускались при запуске приложения, я делаю что-то вроде этого
defmodule Alerts.Scheduler do
use Quantum.Scheduler, otp_app: :alerts
require Logger
@environmet_blacklist [:test]
def init(opts) do
case Enum.member?(@environmet_blacklist, Mix.env()) or IEx.started?() do
true ->
IO.inspect(opts)
opts
false ->
delete_all_jobs()
opts_with_jobs = get_startup_config(opts)
opts_with_jobs |> IO.inspect()
opts_with_jobs
end
end
def get_startup_config(opts) do
job_definition = Alerts.Business.Alerts.get_all_alert_jobs_config()
(opts |> List.delete(List.keyfind(opts, :jobs, 0))) ++ [jobs: job_definition]
end
В моем приложении запуск
def start(_type, _args) do
[
Alerts.Repo,
AlertsWeb.Endpoint |> supervisor([]),
if(System.get_env() != :test, do: Alerts.Scheduler),
Alerts.VersionSupervisor |> supervisor([])
]
|> Supervisor.start_link(strategy: :one_for_one, name: Alerts.Supervisor)
end
Похоже, что Quantum не сохраняет динамически добавленные cronjobs, так как более типичный подход заключается в определении ваших cronjobs (именованных или иных) в вашем config.exs
,
Поскольку вы уже храните данные о работе в Ecto, вам нужно просто прочитать эти данные и прочитать их при запуске приложения. Поскольку вы уже используете Quantum, в config/config.exs
должен сделать трюк:
config :quantum, cron: [
"@reboot": &MyApp.some_function_to_read_and_readd_my_cronjobs/0
]