| name | joblit-codex-batch |
| description | Execute Joblit NEW-job batch tailoring through the versioned AgentCredential protocol in a deterministic, resumable loop. Use for claiming batch tasks, requesting bound CV/Cover prompts, importing strict outputs, and reporting failed or skipped attempts. |
Joblit Codex Batch Skill
Purpose
Run a deterministic, resumable batch loop that generates resume and cover outputs for filtered NEW jobs.
Authentication
Use an AgentCredential minted through the session-only /api/agent-tokens
route — reached from the Runner setup popover in the Joblit nav — for unattended
requests:
Authorization: Bearer jfagent_v1_<64-lowercase-hex-characters>
Content-Type: application/json
The credential must include tailoring:execute. Never send a retired jfext_
token or call session-only batch administration routes with an
AgentCredential.
Required Inputs
batchId (UUID)
maxSteps (default 1, recommended 3-5 per loop)
- Claimed task
protocolVersion (currently literal 1)
- Claimed task
attemptId (UUID)
- Claimed task
issueKey (stable UUID derived by Joblit, reused across retries)
- Claimed
acceptedTargets and remainingTargets
- External model output JSON for each target in
remainingTargets
API Sequence
- Claim tasks
- For an unattended
AgentCredential client, call
POST /api/application-batches/:id/run-once with
{ "maxSteps": 1, "completedTasks": [] }.
- An interactive browser session may instead call
POST /api/application-batches/:id/codex-run.
- Read
tasks[], including each task's attemptId, issueKey,
protocolVersion, acceptedTargets, and remainingTargets, plus
context.generationContract.
- A v1 claim is authoritative: generate and import only
remainingTargets. Never request, regenerate, or re-import a target already
listed in acceptedTargets; its immutable receipt and stored Application
half survive stale reclaim.
- Do not treat batch context as a generation receipt: no concrete job prompt
exists yet.
- Build each missing target prompt
POST /api/applications/prompt once for each target in
remainingTargets with:
jobId
target
source: "codex_batch"
delivery: "FINAL"
protocolVersion: 1 (echo the claim's exact value)
- the claimed task's exact
issueKey
batchId
batchTaskId: taskId
batchAttemptId: attemptId
- Canonical request shape:
{
"jobId": "<tasks[].jobId UUID>",
"target": "resume",
"source": "codex_batch",
"delivery": "FINAL",
"protocolVersion": 1,
"issueKey": "<tasks[].issueKey UUID>",
"batchId": "<batch.id UUID>",
"batchTaskId": "<tasks[].id UUID>",
"batchAttemptId": "<tasks[].attemptId UUID>"
}
- Use returned
prompt and expectedJsonSchema.
- Keep this exact response's
promptMeta; it is bound to the target, prompt
bytes, effective rules, resume snapshot, and job snapshot.
- Keep the returned
tailoringRun handle. Every missing-target request for the
same task must resolve to the same run and current attempt.
- Generate only the current schema returned for that target:
resume: { "cvSummary": string, "latestExperience": { "addedBullets": string[0..3] } }
cover: { "cover": { "paragraphOne": string, "paragraphTwo": string, "paragraphThree": string } }
- Do not emit legacy keys such as
skillsFinal, full experience bullet lists,
or section/header aliases.
- Import generated output
POST /api/applications/manual-generate with:
jobId
target
source: "codex_batch"
modelOutput (strict JSON string)
tailoringRun (the complete, unmodified handle returned with the prompt)
promptMeta (complete, unmodified echo from the target prompt response,
including ruleSetId, resumeSnapshotUpdatedAt,
promptTemplateVersion, schemaVersion, skillPackVersion, and
promptHash)
- Do not add
protocolVersion, issueKey, or batch/task/attempt fields to this
strict import body. Echo the complete tailoringRun handle and promptMeta
returned by the bound prompt request; the server has already bound those
values to the claim identity.
- Treat either the initial PDF response or an exact-replay JSON
acknowledgement (
replayed: true, acceptedDelivery: "FINAL",
x-tailoring-replay: exact) as a successful import. The latter means the
immutable target receipt and Application were already committed before an
earlier HTTP response was lost; do not render or import the target again.
- Report only exceptional task completion
- On the next
AgentCredential
POST /api/application-batches/:id/run-once, include each exceptional result
in completedTasks with the claimed taskId, exact attemptId, and status
FAILED (plus a concise error) or SKIPPED.
- The task
PATCH route is an interactive session-only alternative; do not
call it with an AgentCredential.
- Never send
SUCCEEDED. Importing the final required target atomically commits
the Application, target receipt, Tailoring Run success, and batch task
success.
- Check summary
- Use the latest
run-once response's batch.status and progress.
- An interactive browser session may additionally call
GET /api/application-batches/:id/summary.
Hard Rules
- Always set
source: "codex_batch" on Batch imports.
- Always request prompts with
source: "codex_batch", delivery: "FINAL",
protocolVersion: 1, the batch/task/attempt binding, and the claimed task
issueKey.
- Treat
acceptedTargets as immutable durable work. Only
remainingTargets may be requested, generated, accepted, rendered, or
merged during a reclaimed attempt.
- Never skip, truncate, combine, or synthesize
promptMeta; use the complete
receipt issued for that exact job and target.
- Never skip, alter, or reconstruct
tailoringRun; echo the public handle from
the prompt response into manual-generate.
- Batch generation is current-only. A legacy schema accepted by interactive
manual_import is not valid for codex_batch.
- Keep JSON strict: no markdown wrappers, no prose around JSON.
- Do not fabricate resume facts or unsupported claims.
- Fail fast with concise reason if parsing/validation fails.
- Never expose a private Hermes
run_* identifier to Joblit. The public
Tailoring Run handle is the only run identity in this contract.
Completion Criteria
- No pending tasks in batch summary.
- Every processed task is
SUCCEEDED, FAILED, or SKIPPED.
- Generated PDFs are downloadable from Joblit UI.