# TollRelay for agents

Give every agent a spending limit that sellers check. Three calls, then one header on every request.

## The three calls

1. `POST https://pr-279-api.trlay.sh/identity/orgs` with name, handle, region (eu or us) and a work email. It carries an Idempotency-Key and needs no API key. Returns the organisation id and sends the sign-in link to the work email; signing in is how you get the API key the next two calls present.
2. `POST https://pr-279-api.trlay.sh/identity/machines` with the org id, a label and the public half of a key you made where you run (`public_key` as a JWK, `alg` ed25519, `tier` file). Issues a pass: the identity id and the key's fingerprint. TollRelay never sees the private half.
3. `PUT https://pr-279-api.trlay.sh/mandates/<mid>` with usd_per_day, usd_per_call_max and the sellers allowed. An approver signs it on the trusted surface.

## On every request

Present `X-Trlay-Identity: <JWT>`, your pass, and sign the request with your key per RFC 9421 under the `trlay` label: `Signature-Input`, `Signature` and `Content-Digest`, covering the method, the authority, the path, the query and the body digest, with a fresh nonce, a 30 second window, your key's thumbprint as keyid and `tag="trlay-agent"`. The pass names your key in `cnf.jkt` and is valid only with a request that key signed, once. Your mandate is in the pass; do not exceed it. The SDK checks it before the request leaves, to spare you a call the seller would refuse; the seller and the wallet enforce it.

Mint your own pass with `POST https://pr-279-api.trlay.sh/identity/machines/<mid>/token`, a request signed by your key with your organisation id as `org` in the body and no API key. It lives 15 minutes; mint again before it lapses.

## For sellers

Verify offline: resolve the organisation DID document, check the credential against the trust list at `https://pr-279-api.trlay.sh/.well-known/trlay-trust-list.jws`, and check its status against the status list. Verify online by running the gate at `POST https://pr-279-api.trlay.sh/trust/evaluate`, relaying the pass and the request's `Signature-Input`, `Signature` and `Content-Digest` with its method and URL, which answers a decision, the evidence by class and a receipt id in under 50 ms. A request without a valid signature from the pass's key answers 401 signature_missing, signature_invalid or signature_replayed. `/verify` stays as an alias with the v3 body until Welila cuts over.

A seller can dispute a receipt from its own evaluation with `POST https://pr-279-api.trlay.sh/receipts/<receipt_id>/dispute`, sending the buying organisation (the org claim of the identity token, or the org field of the verify answer) and a reason from a closed list: not_authorised_by_buyer, over_agreed_amount, not_as_described or other. It carries an Idempotency-Key, adds a label with a receipt of its own and leaves the original receipt as it was. A receipt that is not yours answers 404.

## The record

Read the record at `GET https://pr-279-api.trlay.sh/record`: mandate receipts, settlements, wallet activity and verifier events, each with its receipt id, newest first. Add `month=YYYY-MM` for one calendar month in UTC. `/spend` is the former name, kept for one version, and answers the same.

## Discovery

OpenAPI: `https://pr-279-api.trlay.sh/openapi.json`. JWKS: `https://pr-279-api.trlay.sh/.well-known/jwks.json`. MCP: `https://pr-279-api.trlay.sh/mcp` with tools identity, mandate and spend, described at `https://pr-279-api.trlay.sh/.well-known/mcp/server-card.json`. How a bearer credential is presented: `https://pr-279-api.trlay.sh/.well-known/oauth-protected-resource`.
Key directory: each organisation's active agent keys as a JWK Set at `https://<handle>.agents.trlay.dev/.well-known/http-message-signatures-directory`, for a site verifying an agent's edge signature.

## Paying sellers

TollRelay never pays. When a seller answers 402 and names `tollrelay-identity` in its extensions, send the identity with the payment; the seller runs the gate, and the settlement reference lands in your record.
