I have an Elixir app that uses Oban
to schedule jobs at a time specified by users. For example, users can specify the date and time to send a certain email.
Oban works great at scheduling the job initially, and with other features like uniqueness, but I can’t find a sensible way to update the scheduled time of an existing job (when the user wants to change the time).
Currently, two approaches come to mind:
1. Cancel job and queue again
job =
Oban.Job
|> where(fragment("args->>'task_id'") == ^task_id)
|> where([j], j.state in ~w[available scheduled])
|> Repo.one()
Oban.cancel_job(TaskWorker, job.id)
job.args
|> TaskWorker.new(schedule_at: new_time)
|> Oban.insert()
2. Update job manually
Oban.Job
|> where(fragment("args->>'task_id'") == ^task_id)
|> where([j], j.state in ~w[available scheduled])
|> Repo.one()
|> Ecto.Changeset.cast(%{scheduled_at: new_time}, [:scheduled_at])
|> Repo.update()
But I worry that Oban might have its own hooks which do not get called when updating manually or if there’s a better way to do this.
Also posted on Stackoverflow: