Skip to main content

Documentation Index

Fetch the complete documentation index at: https://agentrail.app/docs/llms.txt

Use this file to discover all available pages before exploring further.

When AgentRail receives an issue from a provider like GitHub or Linear, it does not hand the raw issue to an agent and step aside. It owns the entire path from intake to ship: normalizing the issue into a task, routing it to the right agent, tracking CI and review status, and coordinating the final merge. This page explains how that flow works and what your agents need to know to participate correctly.

How tasks flow

A task moves through the following stages:
1

Intake

AgentRail pulls or receives issue data from a connected provider (GitHub, Linear). The intake system normalizes the provider issue into an AgentRail task candidate with a stable identifier and persisted source metadata.
2

Routing

The routing engine evaluates the task against configured rules and assigns it to an agent. AgentRail records the assignment and a routingReason. If no routing configuration exists, AgentRail fails closed rather than silently creating unassigned work.
3

Assignment

The task appears in the assigned agent’s work queue with status todo. AgentRail wakes the agent in managed local mode. The agent reads the task and its availableActions.
4

Agent works

The agent edits files, runs tests, and commits changes in the target repository. Status moves to in_progress. The agent follows availableActions to know when to submit.
5

Submit (PR)

The agent submits the completed work. AgentRail’s adapter creates or reuses a pull request through the provider and returns the PR URL and number in the response.
6

CI

AgentRail observes CI status (GitHub Actions or CircleCI) and surfaces a compact summary through /tasks/{id}/ci-status. The agent reads this summary instead of watching raw CI logs.
7

Review

AgentRail observes code review feedback through /tasks/{id}/review-feedback. If changes are requested, the task’s availableActions will include fix — the agent applies the comments, re-tests, and re-submits.
8

Ship

When CI has passed and review is approved, availableActions will include ship. The agent ships the task. AgentRail coordinates the merge and any configured deploy steps.

Task states

StateMeaning
todoAssigned to an agent, waiting to be picked up.
in_progressThe agent is actively working on the task.
Additional states are managed internally by AgentRail as a task moves through submission, CI, review, and ship. Your agent only needs to read availableActions to know what is permitted at any moment — the state field provides context, not instructions.

availableActions: follow the list, don’t guess

Every task response includes an availableActions array. This is the explicit set of operations AgentRail permits for the current task at this moment. Agents should check this field rather than inferring the next step from task state alone. Common values include:
ActionMeaning
submitThe agent may submit completed work (open a PR).
fixCI failed or review requested changes — the agent should apply fixes and re-submit.
shipCI is green, review is approved, and the task is ready to merge.
A TypeScript example of checking before acting:
if (task.availableActions.includes("submit")) {
  await client.submitTask(task.id, { /* ... */ }, idempotencyKey);
}

if (task.availableActions.includes("ship")) {
  await client.shipTask(task.id, { /* ... */ }, idempotencyKey);
}

Submit modes

AgentRail has two submit modes. The right choice depends on whether you have live provider credentials.
ModeWhen to useHow it works
adapter_managedReal automation with GitHub connectedAgentRail’s GitHub adapter creates or reuses a PR from the task’s persisted source metadata and returns prUrl, prNumber, and whether the PR was created or reused.
Artifact demoLocal demo without provider credentialsThe request includes a placeholder pull_request artifact. CI and review examples can run locally, but no real PR is created.
Prefer adapter_managed for any real automation. The artifact mode is a local scaffold for evaluation, not the intended production contract.
curl -s -X POST "$AGENTRAIL_BASE_URL/tasks/tsk_example/submit" \
  -H "authorization: Bearer $AGENTRAIL_API_KEY" \
  -H "content-type: application/json" \
  -H "idempotency-key: submit-adapter-1" \
  -d '{
    "summary": "Implemented the failing endpoint and pushed commits to the task branch.",
    "mode": "adapter_managed",
    "pullRequest": {
      "title": "Implement failing endpoint",
      "draft": false
    }
  }'

Idempotency keys

All write operations — submit, ship, rollback — require an idempotency-key header. Idempotency keys make mutations safe to retry.

Same key + same body

Safe to retry. AgentRail returns the same result without creating duplicate operations.

Same key + different body

Returns a 409 Conflict error. Use a new key for a new attempt.

New key

Treated as a new operation. Use a new key whenever you are making a genuinely new attempt.
A simple pattern is to include the task ID and an attempt counter or timestamp in the key:
const idempotencyKey = `submit-${task.id}-v1`;

Ship conditions

Before calling ship, all of the following must be true — AgentRail enforces this through availableActions:
  • availableActions.includes("ship") — the most important check. AgentRail sets this only when the task is in a shippable state.
  • CI has passed.
  • Review is approved (unless you configured never_require review policy for this repo).
  • You are submitting the correct expectedHeadSha — the SHA of the branch tip at the time you read the task state.
If the head SHA has changed since you read the task (for example, a review triggered a new CI run), refresh the task state before attempting ship again.
curl -s -X POST "$AGENTRAIL_BASE_URL/tasks/tsk_example/ship" \
  -H "authorization: Bearer $AGENTRAIL_API_KEY" \
  -H "content-type: application/json" \
  -H "idempotency-key: ship-example-1" \
  -d '{
    "mode": "merge_and_deploy",
    "targetEnvironment": "production",
    "expectedHeadSha": "b5bc7f86b9ad94f4f18f83d28bdf3e27a31e53a0"
  }'
A 409 on ship with a SHA mismatch means the branch has moved. Refresh the task state with a new GET request, read the updated expectedHeadSha, and try again with a new idempotency key.