56 lines
1.6 KiB
Elixir
56 lines
1.6 KiB
Elixir
defmodule Mix.Tasks.JoinRequests.CleanupExpired do
|
|
@moduledoc """
|
|
Hard-deletes JoinRequests in status `pending_confirmation` whose confirmation link has expired.
|
|
|
|
Retention: records with `confirmation_token_expires_at` older than now are deleted.
|
|
Intended for cron or Oban (e.g. every hour). See docs/onboarding-join-concept.md.
|
|
|
|
## Usage
|
|
|
|
mix join_requests.cleanup_expired
|
|
|
|
## Examples
|
|
|
|
$ mix join_requests.cleanup_expired
|
|
Deleted 3 expired join request(s).
|
|
"""
|
|
use Mix.Task
|
|
|
|
require Ash.Query
|
|
|
|
alias Mv.Membership.JoinRequest
|
|
|
|
@shortdoc "Deletes join requests in pending_confirmation with expired confirmation token"
|
|
|
|
@impl Mix.Task
|
|
def run(_args) do
|
|
Mix.Task.run("app.start")
|
|
|
|
now = DateTime.utc_now()
|
|
|
|
query =
|
|
JoinRequest
|
|
|> Ash.Query.filter(status == :pending_confirmation)
|
|
|> Ash.Query.filter(confirmation_token_expires_at < ^now)
|
|
|
|
# Bypass authorization: cleanup is a system maintenance task (cron/Oban).
|
|
case Ash.read(query, domain: Mv.Membership, authorize?: false) do
|
|
{:ok, requests} ->
|
|
count = delete_expired_requests(requests)
|
|
Mix.shell().info("Deleted #{count} expired join request(s).")
|
|
count
|
|
|
|
{:error, error} ->
|
|
Mix.raise("Failed to list expired join requests: #{inspect(error)}")
|
|
end
|
|
end
|
|
|
|
defp delete_expired_requests(requests) do
|
|
Enum.reduce_while(requests, 0, fn request, acc ->
|
|
case Ash.destroy(request, domain: Mv.Membership, authorize?: false) do
|
|
:ok -> {:cont, acc + 1}
|
|
{:error, _} -> {:halt, acc}
|
|
end
|
|
end)
|
|
end
|
|
end
|