Adds backfill job to startup tasks

This commit is contained in:
Kieran Eglin 2024-03-10 15:10:46 -07:00
parent bc24ac3808
commit bc25bf67e4
No known key found for this signature in database
GPG key ID: 193984967FCF432D
4 changed files with 66 additions and 4 deletions

View file

@ -10,9 +10,9 @@ defmodule Pinchflat.Application do
children = [
PinchflatWeb.Telemetry,
Pinchflat.Repo,
# {Task, &run_startup_tasks/0},
Pinchflat.StartupTasks,
# Must be before startup tasks
{Oban, Application.fetch_env!(:pinchflat, Oban)},
Pinchflat.StartupTasks,
{DNSCluster, query: Application.get_env(:pinchflat, :dns_cluster_query) || :ignore},
{Phoenix.PubSub, name: Pinchflat.PubSub},
# Start the Finch HTTP client for sending emails

View file

@ -8,8 +8,11 @@ defmodule Pinchflat.StartupTasks do
# restart: :temporary means that this process will never be restarted (ie: will run once and then die)
use GenServer, restart: :temporary
import Ecto.Query, warn: false
alias Pinchflat.Repo
alias Pinchflat.Settings
alias Pinchflat.Workers.DataBackfillWorker
def start_link(opts \\ []) do
GenServer.start_link(__MODULE__, %{}, opts)
@ -21,11 +24,13 @@ defmodule Pinchflat.StartupTasks do
Any code defined here will run every time the application starts. You must
make sure that the code is idempotent and safe to run multiple times.
This is a good place to set up default settings, create initial records, stuff like that
This is a good place to set up default settings, create initial records, stuff like that.
Should be fast - anything with the potential to be slow should be kicked off as a job instead.
"""
@impl true
def init(state) do
apply_default_settings()
enqueue_backfill_worker()
{:ok, state}
end
@ -34,4 +39,12 @@ defmodule Pinchflat.StartupTasks do
Settings.fetch!(:onboarding, true)
Settings.fetch!(:pro_enabled, false)
end
defp enqueue_backfill_worker do
DataBackfillWorker.cancel_pending_backfill_jobs()
%{}
|> DataBackfillWorker.new()
|> Repo.insert_unique_job()
end
end

View file

@ -14,11 +14,24 @@ defmodule Pinchflat.Workers.DataBackfillWorker do
# I'm just trying out that pattern and seeing if I like it better
# so this may change.
import Ecto.Query, warn: false
require Logger
alias __MODULE__
alias Pinchflat.Repo
alias Pinchflat.Media.MediaItem
@doc """
Cancels all pending backfill jobs. Useful for ensuring worker runs immediately
on app boot.
Returns {:ok, integer()}
"""
def cancel_pending_backfill_jobs do
Oban.Job
|> where(worker: "Pinchflat.Workers.DataBackfillWorker")
|> Oban.cancel_all_jobs()
end
@impl Oban.Worker
@doc """
Performs one-off tasks to get data in the right shape.
@ -30,6 +43,7 @@ defmodule Pinchflat.Workers.DataBackfillWorker do
Returns :ok
"""
def perform(%Oban.Job{}) do
Logger.info("Running data backfill worker")
backfill_shorts_data()
reschedule_backfill()
@ -45,7 +59,9 @@ defmodule Pinchflat.Workers.DataBackfillWorker do
where: m.short_form_content == false
)
Repo.update_all(query, set: [short_form_content: true])
{count, _} = Repo.update_all(query, set: [short_form_content: true])
Logger.info("Backfill worker set short_form_content to true for #{count} media items.")
end
defp reschedule_backfill do

View file

@ -4,8 +4,41 @@ defmodule Pinchflat.Workers.DataBackfillWorkerTest do
import Pinchflat.MediaFixtures
alias Pinchflat.Workers.DataBackfillWorker
alias Pinchflat.Workers.FilesystemDataWorker
describe "cancel_pending_backfill_jobs/0" do
test "cancels all pending backfill jobs" do
%{}
|> DataBackfillWorker.new()
|> Repo.insert_unique_job()
assert_enqueued(worker: DataBackfillWorker)
DataBackfillWorker.cancel_pending_backfill_jobs()
refute_enqueued(worker: DataBackfillWorker)
end
test "does not cancel jobs for other workers" do
%{id: 0}
|> FilesystemDataWorker.new()
|> Repo.insert_unique_job()
assert_enqueued(worker: FilesystemDataWorker)
DataBackfillWorker.cancel_pending_backfill_jobs()
assert_enqueued(worker: FilesystemDataWorker)
end
end
describe "perform/1" do
setup do
DataBackfillWorker.cancel_pending_backfill_jobs()
:ok
end
test "reschedules itself once complete" do
perform_job(DataBackfillWorker, %{})