Documentation Developers

HTTP API reference

The actual hosted endpoints, request fields, access rules and error handling.

Conventions & authentication

All paths start with /api. Reads use GET; mutations use POST with Content-Type: application/json. JSON bodies are capped at20KB. Responses are JSON with Cache-Control: no-store, except the ZIP download. Errors include an error string.

Account identity comes from a verified ERC-4361 Ethereum wallet signature and an opaque HttpOnly cookie session in D1. A connected address or oai-authenticated-* header does not authenticate a user. Sign-in messages expire after five minutes and are bound to this browser and origin; sessions expire after seven days. Same-origin JSON POST requests are required for authentication and authenticated mutations. The run bearer token works only for that run’s read/action paths.

const r = await fetch("/api/worlds/return-terminal/runs", {
  method: "POST",
  headers: {"Content-Type":"application/json"},
  body: JSON.stringify({nonce: crypto.randomUUID()})
});
const {run, agentToken} = await r.json();
// Call from an authenticated same-origin session. Store capability privately.

Endpoint map

Method + pathRequest / result
GET /healthD1 health, app version and financial deployment status.
GET /mesignedIn and linked wallet (if any).
POST /auth/challenge{address,chainId}; same-origin only; returns one-use SIWE message and sets a browser-bound challenge cookie.
POST /auth/verify{id,signature}; verifies that exact challenge and sets a seven-day HttpOnly session. Keep cookies; never send a private key.
POST /auth/logout{}; revokes the current server session and clears authentication cookies.
GET /worldsPublished catalog. Add ?mine for owner drafts; sign-in required.
POST /worlds{name,description,spec,nonce}; creates an owned draft.
GET /worlds/:idWorld specification and isOwner.
POST /worlds/:id/validate{}; owner-only deterministic reference checks.
POST /worlds/:id/publish{rights:true,creatorName}; validates/pins owner’s draft.
GET /worlds/:id/artifactPublished ZIP evaluation package.
POST /worlds/:id/archive{}; owner only, only without registered market.
POST /worlds/:id/runs{nonce:UUID}; signed-in run creation; capability returned once.
GET /runsOwner’s run history.
GET /runs/:idOwner or run capability; run, policy if read, action receipts.
POST /runs/:id/actions{revision,key:UUID,action}; owner/capability; atomic revision + receipt.
POST /wallet/challenge{address}; optional creator-wallet re-verification; address must match the signed-in wallet.
POST /wallet/verify{id,signature}; verifies challenge and links wallet.
POST /worlds/:id/market{address,chainId:4663}; owner; verifies chain/bytecode/asset/terms/creator.

World creation body

{
  "name":"My Returns World",
  "description":"Tests return windows and untrusted customer notes.",
  "nonce":"A_NEW_UUID",
  "spec":{
    "version":1,"template":"returns","brand":"Orbit Supply",
    "returnDays":30,"scenarios":6,"difficulty":"adversarial","seed":42
  }
}

Errors, limits & retries

Creating a run with the same nonce returns its existing run. A retry does not reissue the bearer capability: the repeated response has agentToken:null. Public high-volume operation needs additional edge rate limits.

StatusResponse
400Invalid payload/action or contract verification failed; inspect error.
401 / 403Sign in or use the correct run capability/account.
404World/run not found.
409State changed: reload latest revision. Existing idempotency key replays its stored result.
410Run expired for writes; create a new run.
413 / 415Body over20KB / incorrect JSON content type.
429Per-account limit reached. Current run creation cap100 per24hours.
503Storage unavailable; retry later without inventing local success.

Examples explain the implemented mechanics. Live market status belongs to the individual world. No guaranteed buyer, yield or training improvement.