ObanCodex.Agent.Job (oban_codex v0.2.0)

Copy Markdown View Source

The default Oban worker for agent turns: runs Codex, then routes the outcome back to the owning ObanCodex.Agent.Instance.

The owning agent's id, instance generation, and logical turn id ride in the job's meta, where ObanCodex.Agent.Instance puts them at enqueue time. The generation prevents a job from an earlier same-id process from controlling its replacement. The turn id keeps retries attached to one logical turn and fences late or duplicate callbacks. A job without an "agent_id" (enqueued by hand) runs normally and reports to no one.

Retry-awareness

The routing is terminal-aware, so a worker with retries reports one logical turn, not one event per attempt:

  • a success, a {:cancel, _} verdict, or an {:error, _} on the final attempt is terminal -> ObanCodex.Agent.job_finished/3
  • an {:error, _} with attempts remaining, or a {:snooze, _}, means Oban will re-run the job -> ObanCodex.Agent.job_retrying/3, which keeps the machine in :running and re-arms its watchdog

This worker itself stays at max_attempts: 1 -- every retry is a fresh paid Codex call, so retrying is an explicit opt-in, not a default. To opt in, point the agent's :worker config at your own worker and delegate the callbacks here:

defmodule MyApp.RetryingAgentJob do
  use ObanCodex.Worker, queue: :agents, max_attempts: 3

  @impl ObanCodex.Worker
  def handle_result(result, job), do: ObanCodex.Agent.Job.handle_result(result, job)

  @impl ObanCodex.Worker
  def handle_error(verdict, payload, job),
    do: ObanCodex.Agent.Job.handle_error(verdict, payload, job)
end