Source: schemas/wire_errors.json
Generated automatically from the published contract sources.
Source path: schemas/wire_errors.json.
Complete source
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "Turn Zero Cloud — refusal names, contract version 1",
"version": "2026-10-07.1",
"description": "Every refusal name a surface of the platform answers (MAPI-15 in the management API contract), listed once with the surfaces answering it, the HTTP status where one status is fixed across every site (null where it varies or the name is recorded rather than answered), the statement owning the behaviour (null where no statement names it), and a one-clause summary. The list is pinned by a test in the platform's suite against the source: a name the source answers and this list lacks, or a name this list carries and the source no longer answers, fails that suite. The JSON refusal bodies of the management action surface follow wire_error.schema.json, and the body another surface answers under a name of this list is stated by that surface's owning statement, in the shape the surface answers (MAPI-15). A row's members, where it carries them, state the members the refusal's body carries on the management action surface beyond the six base members of wire_error.schema.json, each typed and described by a schema fragment, and state nothing of another surface's body under the same name. This inventory also includes standard OAuth error parameters in WWW-Authenticate challenge headers and authorization redirects, whose protocol shapes remain their own.",
"surfaces": {
"management_action": "An action of schemas/management_api.json, on its HTTP route and through the MCP tool that surfaces it (MAPI-08); a refusal recorded on a pending action is read through read_pending_action.",
"mcp_server": "The MCP transport’s refusals for protected tool calls and resource reads, and the tool dispatch surface.",
"storage": "The object storage surface under /storage/v0 (OST-L0-01 through OST-L0-08).",
"egress": "The egress gateway under /egress/v0 (EGW-L0-01 through EGW-L0-09, and EGW-L0-18 for the day limit).",
"realm_surface": "The accounts service: the end-user sign-in, passkey, session, and deletion routes on the application hostname (ACS-L0-01 through ACS-L0-10), the platform-origin callback pages, and the verification route /accounts/v0/verify (ACS-L0-06).",
"builder_sign_in": "The builder realm on the control plane: the OAuth authorization-server routes (MCP-02), the builder passkey routes (ACS-L0-10), the linking and interrupt routes (ACB-L0-03), and the invitation redemption route (ACS-L0-08; ACB-L0-77). Turn Zero Blueprint's request for one issue space's token is among the OAuth routes, and the management service serves its confirm page and its code exchange under /approve/blueprint/ (MCP-02).",
"router": "The serving router on the application hostnames (SVC-L0-07) and the platform-internal resolve endpoint it reads.",
"egress_tunnel": "The egress tunnel seat in the hosting cell — the HTTP CONNECT proxy of the tunnel mode (EGW-L0-11; EGW-L0-16). A refusal is a 403, or 429 at one of the application's egress limits, with 407 for the credential, 502 for a failed dial, and 503 for an unanswered declaration read. The X-Egress-Refusal header names it and the body is { contract_version, error, detail, host, port }; egress_undeclared's carries its remedy beside them and a limit's the count, the limit, and the reset (EGW-L0-14; EGW-L0-18). Every refusal is also a row of the seat's establishment record (EGW-L0-14).",
"logging": "The logging ingest under /logging/v0 (the logging package's wire statement; read through read_logs and read_counters).",
"harness": "The runtime harness inside every application container — the inbound guard (HST-L0-01; SVC-L0-07 as amended) and the bounded execution window's abort half (HST-L0-03). The abort half's two records, `window_ended` and `process_ended`, are written to the container's console log rather than answered on the wire. The source is Node.js Runtime's boot module, which the pin test reads beside the platform's own source.",
"documentation": "The authenticated machine files of the documentation trees (PLD-L0-69), a gated tree answering a connection whose account holds the tree; MCP documentation reads use the mcp_server surface.",
"push": "The push service's send route under /push/v0, taken under the platform credential alone.",
"deploy_progress": "The deploy command's progress read: the read the turnzero-cloud command makes under the upload grant its preparing `deploy` call answered, from that grant's start until five minutes after the deploy ends, never past fifteen minutes after the start (PLD-L0-86). It answers plain text lines, and a refusal is a JSON body of `contract_version`, `error`, and `detail`.",
"workflow_start": "The platform's own start-line route, which Turn Zero's scheduled hosted workflows call to record that a run started, presenting the run's identity token from GitHub, and which no customer calls (PLD-L0-76). A refusal is a JSON body of `contract_version`, `error`, and `detail`."
},
"refusals": [
{
"name": "access_denied",
"surfaces": [
"builder_sign_in"
],
"status": 302,
"owner": "MCP-02",
"summary": "The person declined at the identity provider, or cancelled on Turn Zero Blueprint's confirm page; the OAuth answer carried on the client redirect as error=access_denied, nothing minted.",
"remedy": "Start the sign-in again from your tool or the command, and accept at the identity provider or confirm on the page."
},
{
"name": "account_credential_required",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "PLD-L0-47",
"summary": "This refusal answers halt_environment on the production environment reached by a minted token bounded to one application. Stopping production is an account action. It is admitted under the account's session or an account-wide minted token alone, so that a leaked application-bounded token cannot stop production. resume_environment on either environment and the development halt keep the bounded token's admission.",
"remedy": "Repeat halt_environment on production under your account's session, or under a token minted with mint_token for the whole account.",
"members": {
"scope": {
"type": "object",
"description": "The bound of the token presented: a token minted for one application, under which halting production is refused.",
"properties": {
"kind": {
"type": "string",
"description": "The kind of bound, always application here."
},
"application": {
"type": "string",
"description": "The id of the application the token is bounded to."
}
}
}
}
},
{
"name": "account_not_synthetic",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAPI-16",
"summary": "purge_synthetic_accounts, read_synthetic_signin_code, or read_synthetic_account_state named an account that stands and is not synthetic. The purge refuses whole and deletes nothing, because a customer's account is deleted through delete_account and its browser approval alone (API-L0-07), and the reads answer nothing of a customer's sign-in or state. The refusal names the accounts. A purge under the synthetic_seed_purge grant, and the two reads under synthetic_estate, answer account_outside_batches for such an account instead, the reach read first.",
"remedy": "Remove the accounts the refusal names from your request, then repeat. To delete a customer's account, call delete_account and give its browser approval.",
"members": {
"accounts": {
"type": "array",
"items": {
"type": "string"
},
"description": "The account ids the request named that stand and are not synthetic, as the caller wrote them. The list is never empty."
}
}
},
{
"name": "account_outside_batches",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAPI-16",
"summary": "The purge, the sign-in code read, or the state read, under a synthetic grant, named a synthetic account outside the caller's reach. Under synthetic_estate the reach is the batches the caller's own credential seeded and every first-sign-in batch; under synthetic_seed_purge it is the batches the caller's own credential seeded alone. Outside it is a batch a session seeded, a batch another credential seeded, or an account seeded before batches carried a credential. purge_synthetic_accounts answers it under either grant, and the two reads under synthetic_estate. The refusal names the accounts, and the purge's names the grant that bounds the caller. Under synthetic_seed_purge the purge, and under synthetic_estate the two reads, read it ahead of account_not_synthetic, so they answer every named id outside the caller's reach, a customer's account and an id no account holds among them. Under that grant it also answers a purge whose request_id another credential's purge carries, naming no account.",
"remedy": "Name accounts your own credential seeded, or repeat from a credential holding super_admin, which reaches every synthetic account. Where the refusal names no account, repeat the purge under another request_id.",
"members": {
"accounts": {
"type": "array",
"items": {
"type": "string"
},
"description": "The account ids the request named that lie in no batch the caller's own credential seeded, as the caller wrote them. The list is never empty. The member is left out where the request repeated a request_id another credential's purge carries."
},
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The synthetic grant that bounds the caller's credential, present on the purge's refusal."
}
}
},
{
"name": "account_suspended",
"surfaces": [
"management_action",
"router",
"egress_tunnel",
"builder_sign_in",
"mcp_server",
"storage",
"egress",
"realm_surface",
"documentation",
"logging",
"push",
"deploy_progress"
],
"status": null,
"owner": "API-L0-12",
"summary": "The acting account (403, management), the owning account of the served hostname (503, router), or the calling application's account at the tunnel seat (403) is suspended. A suspended account's sign-in completion, a provider leg's or a passkey assertion's, is refused by this name on the builder sign-in surface (403, ACS-L0-11). At that refusal, no session is minted, no cookie is set, and no code is issued. While the account a grant records as its owner is suspended, the grant is refused by this name (403): a transfer grant on the storage surface, an upload grant on the deploy command's progress read, and a secret grant on its one write. The grant serves again once the account is reinstated, within its expiry. On the egress surface, an egress key is refused by this name (403) while its owning account is suspended. reinstate_account is the way back. Turn Zero Blueprint's confirm page and code exchange answer it for a suspension after the sign-in, the page's link returning it.",
"remedy": "Nothing on the caller's side corrects this. Only the platform operator restores the account through reinstate_account, and the request succeeds again once the account is reinstated."
},
{
"name": "address_held_by_another_account",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACB-L0-03",
"summary": "The linking write refuses a route whose provider-verified address a different account of the realm holds. One verified address is one account (ACC-L0-04). Nothing is bound and nothing is merged. The refusal is answered on the link_identity add leg's callback page and the interrupt's link exit, on the builder realm and on an end-user realm alike.",
"remedy": "Authenticate as the account that holds that address, through one of its existing routes or the code sent to that mailbox, then complete the link from there."
},
{
"name": "address_not_synthetic",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAPI-16",
"summary": "read_synthetic_signin_code was called by address with an address outside the reserved fixture domain synthetic.turnzero.ai. The read answers the codes held for an address at that domain alone — a first sign-in's, held under the address until its confirmation creates the account, and a synthetic account's own after — so nothing is answered, and the refusal carries no address.",
"remedy": "Name an address at the fixture domain in `address`, or the synthetic account's id in `account`, then repeat."
},
{
"name": "allowance_application_required",
"surfaces": [
"egress"
],
"status": 403,
"owner": "EGW-L0-08",
"summary": "The platform upstream ai-allowance is reached by an application's platform credential or a minted token bounded to an application alone, because the allowance is the application's and interactive work never draws it (PRC-L0-06); an account-wide session or token is refused by name.",
"remedy": "Make the call under the application's own platform credential, or under a token that mint_token bounds to that one application. For a local run, use the development environment's platform credential rather than your own sign-in."
},
{
"name": "allowance_busy",
"surfaces": [
"egress"
],
"status": 429,
"owner": "EGW-L0-06",
"summary": "The application already has as many allowance calls in flight on this gateway replica as the platform admits at once (the AI_ALLOWANCE_MAX_CONCURRENT setting), so the call is refused by name and the application retries after one of them ends.",
"remedy": "Wait for one of the application's allowance calls already in flight to finish, then repeat the request."
},
{
"name": "allowance_exhausted",
"surfaces": [
"egress"
],
"status": 429,
"owner": "EGW-L0-06",
"summary": "The application's included AI allowance for the current UTC month is drawn. The month's units, drawn by the platform upstream's passed calls and by its calls forwarded to the provider and then ended early, plus the calls in flight on the replica, stand at or past the plan's gemini-flash-allowance quantity. The call is therefore refused at the boundary with resets_at, the next UTC month's first instant. The ways for the application to continue are a larger plan or its own stored key on its own declared upstream (PRC-L0-06).",
"remedy": "Move the application to a larger plan with set_plan, or store your own key with store_secret, declare the upstream with declare_upstream, and call through it. Otherwise wait for the instant resets_at names, the first instant of the next UTC month, then repeat the request."
},
{
"name": "allowance_feature_refused",
"surfaces": [
"egress"
],
"status": 400,
"owner": "EGW-L0-01",
"summary": "The allowance call's body is not JSON, or asks for a feature priced apart from tokens (tools, cached content, or an output modality other than text). The included allowance does not cover such a feature (PRC-L0-06). The call is refused by name before any key is read.",
"remedy": "Send a JSON body that asks for text generation alone: no tools, no cached content, and no output modality other than text. For one of those features, declare an upstream on your own stored key and call it there."
},
{
"name": "allowance_path_refused",
"surfaces": [
"egress"
],
"status": 403,
"owner": "EGW-L0-01",
"summary": "The platform upstream ai-allowance admits one request shape: POST to the text-generation method of a model the platform admits (the AI_ALLOWANCE_MODELS setting). Any other path, method, or model is refused by name, so the platform key pays for text generation on the admitted models and nothing else (PRC-L0-06).",
"remedy": "Send a POST to /v1beta/models/<model>:generateContent or :streamGenerateContent, naming a model the platform admits. For another model, method, or path, declare an upstream on your own stored key and call it there."
},
{
"name": "allowance_unavailable",
"surfaces": [
"egress"
],
"status": 503,
"owner": "EGW-L0-01",
"summary": "The platform holds no key for the included AI allowance: the gateway setting names no vault secret, or the core vault holds no version under the name, so no allowance call is carried until the operator stores the key (the credential register's ai_allowance_key row).",
"remedy": "Nothing on the caller's side corrects this, because the platform's operator alone stores the allowance key. Until the key is stored, call a declared upstream on your own stored key."
},
{
"name": "app_credential_not_admitted",
"surfaces": [
"management_action",
"mcp_server"
],
"status": null,
"owner": "SEC-L0-07",
"summary": "The application platform credential is admitted by read_account alone on the management plane (403) and connects nothing at the MCP server (401 challenge).",
"remedy": "Sign in through your connected tool, or present a token minted by mint_token, and repeat the call. Present the application's platform credential only on the storage and egress routes, on the end-user verification route, and on read_account."
},
{
"name": "application_credential_required",
"surfaces": [
"logging"
],
"status": 403,
"owner": null,
"summary": "The logging ingest admits the application platform credential and an application-bounded minted token alone; an account credential names no stream.",
"remedy": "Send the batch under the application's platform credential, or under a token bounded to that one application. Mint such a token with mint_token where none is held."
},
{
"name": "application_required",
"surfaces": [
"management_action",
"storage"
],
"status": 400,
"owner": "OST-L0-01",
"summary": "A storage area or an upstream was declared under an account-wide credential with no application named.",
"remedy": "Name the application the area or upstream binds to: the identifier list_applications answers. Every area and every upstream binds to one application; on the storage wire a mint under the application’s platform credential or a token bounded to one application may omit the member, which then names that application."
},
{
"name": "approval_expired",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action expired before the browser approved or declined it.",
"remedy": "Request the action again where it is still wanted. The new request creates a new pending action with its own approval link to approve in the browser."
},
{
"name": "approval_not_found",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "API-L0-07",
"summary": "No pending action by that id reached approve or decline.",
"remedy": "Open the approval link exactly as your session printed it. Where read_pending_action from the requesting tool also finds no record, request the action again."
},
{
"name": "approval_state_approved",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action is already approved; approve and decline act on the requested state alone.",
"remedy": "No further click is needed. Read the outcome through read_pending_action from the requesting tool."
},
{
"name": "approval_state_completed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action already completed; approve and decline act on the requested state alone.",
"remedy": "Nothing remains to approve or decline. Read the recorded outcome through read_pending_action from the requesting tool."
},
{
"name": "approval_state_declined",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action is already declined; approve and decline act on the requested state alone.",
"remedy": "Where the act is still wanted, request it again. The new request creates a new pending action with its own approval link to approve in the browser."
},
{
"name": "approval_state_executing",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action is executing; approve and decline act on the requested state alone.",
"remedy": "Wait for the execution to finish, then read the outcome through read_pending_action from the requesting tool. No further click is needed."
},
{
"name": "approval_state_expired",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action is already in the expired state; approve and decline act on the requested state alone.",
"remedy": "Request the action again where it is still wanted. The new request creates a new pending action with its own approval link to approve in the browser."
},
{
"name": "approval_state_failed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action already failed; approve and decline act on the requested state alone.",
"remedy": "Read the outcome through read_pending_action and check the subject's current state. Where the act is still wanted, request it again and approve the new pending action in the browser."
},
{
"name": "approval_state_gone",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-07",
"summary": "The pending action row disappeared between the compare and the set of the PostgreSQL store.",
"remedy": "Read the record through read_pending_action from the requesting tool. Where it no longer exists, request the action again and approve the new pending action in the browser."
},
{
"name": "approval_wrong_account",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "API-L0-07",
"summary": "The approving browser session belongs to an account other than the requesting one.",
"remedy": "Sign in to the browser as the account that made the request, then open the approval link again."
},
{
"name": "area_name_reserved",
"surfaces": [
"management_action",
"storage"
],
"status": 400,
"owner": "OST-L0-01",
"summary": "A new storage area was declared under a name beginning `export-` or `deploy-`, the prefixes of the export areas the platform mints for request_export and of the deploy areas it mints for deploy's upload form. The refusal stands on the minting route and through declare_storage_area; an area standing under either prefix redeclares as any area does.",
"remedy": "Declare the area under a name that begins with neither `export-` nor `deploy-`. An application's export area is the platform's: request_export mints it, and the line mint_download_grant answers downloads its files. An application's deploy area is the platform's too: deploy's upload form mints it and writes to it."
},
{
"name": "area_not_empty",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "OST-L0-01",
"summary": "An undeclare named a storage area that holds a file in one of its environment partitions; the declaration stands.",
"remedy": "Remove the files first through the storage routes, from both environments' partitions, then undeclare the area again; or keep the area."
},
{
"name": "area_scope_refused",
"surfaces": [
"management_action",
"storage"
],
"status": 403,
"owner": "OST-L0-03",
"summary": "The credential does not reach the area. An area admits its own application and an account-wide credential that no bounding grant bounds. A minted token the synthetic_seed_purge, synthetic_estate, publication, feedback_queue, or issues grant bounds reaches no area of the account (MAPI-16). On mint_upload_grant, the named area is bound to an application other than the one the call names. On mint_download_grant, the credential does not reach the export area. On the platform's deploy area, `deploy-<application id>`, only the upload grant `deploy` answers reaches the file routes, and every other credential is refused, the account's own included.",
"remedy": "Repeat the request with a credential the area admits: an account-wide credential that no bounding grant bounds, or the credential of the application the area is bound to. A wider reach is a second token, minted from a signed-in session through mint_token, never an edit to the held one. For a token the synthetic_seed_purge, synthetic_estate, publication, feedback_queue, or issues grant bounds, mint a token without the grant, or call from the owner's session. For mint_upload_grant, name the application the area is bound to, or an area bound to the named application. For the deploy area, deploy by a line: call `deploy` with the application, naming no environment and none of `zip_sha256`, `artifact`, and `upload`, run the line it answers once, as given, from the application's folder, and make its `next` call. No credential of yours reads, lists, or deletes that area's files."
},
{
"name": "artifact_area_mismatch",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "PLD-L0-63",
"summary": "deploy: the artifact's area is one the artifact form cannot read. A deploy reads its artifact from an area bound to that application alone, OST-L0-03's reach rule applied to the deploy's own read. An area the account has not declared, one bound to another application of the account, and the platform's deploy area, `deploy-<application id>`, are refused before any byte is read.",
"remedy": "Upload the artifact into an area declared with the application you deploy — declare_storage_area with that application, or the application's own credential on the minting route — then call deploy naming that area. An area binds to one application at its declaration and is never re-pointed, so an artifact for another application goes into an area of its own. A zip in the deploy area is deployed by the upload form: `deploy` naming the `upload` its preparing call answered."
},
{
"name": "artifact_hash_mismatch",
"surfaces": [
"management_action"
],
"status": 400,
"owner": null,
"summary": "deploy: the artifact bytes in the acting account area hash to a value other than the one the request names.",
"remedy": "Recompute the stored file's hash, or upload the intended bytes again, then call deploy naming the stored file's hash."
},
{
"name": "artifact_layout_invalid",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-63",
"summary": "deploy: the zip's layout cannot run. It holds no root package.json that parses as a JSON object, or neither a scripts.start nor a root server.js for npm start to run, or a root package.json or manifest.json declaring more than 1 MiB. So is a zip past 65,535 entries, 128 MiB declared by its files and folders, or 500,000 name segments. An entry name the image build refuses is refused too: one longer than 4,096 bytes or 128 segments, with a backslash or a NUL, a drive, or an absolute or climbing path, or one path named as both a file and a folder. So is a workspaces pattern the platform does not read, a root manifest.json nested past 64 levels, and a root or workspace member binding.gyp with no .node file in its folder. The detail names the cause. No version row is inserted and no deploy is counted.",
"remedy": "Zip the contents of the folder that holds package.json rather than the folder itself, give package.json a start script naming the server's entry, upload the zip, and call deploy again. On Windows, build the zip with the tar.exe command the detail and step 3 of read_documentation's page /cloud/getting-started/deploy-an-application/ give, since Compress-Archive writes a backslash between segments. Ship the root's or a workspace member's native module prebuilt, with its .node file where step 3 of read_documentation's page /cloud/getting-started/deploy-an-application/ says."
},
{
"name": "artifact_not_found",
"surfaces": [
"management_action"
],
"status": 404,
"owner": null,
"summary": "deploy: no file by the named area and name in the acting account partition.",
"remedy": "Upload the artifact into one of the acting account's storage areas, then call deploy naming that area and file name. Name the environment whose partition holds the file where that is not the environment deployed."
},
{
"name": "artifact_unreadable",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-63",
"summary": "deploy: the artifact's bytes do not read as a zip archive, or an entry the deploy reads inflates past the size it declares, the detail naming the entry. The deploy reads the zip directly after its bytes and hash, before the in-flight check and the plan's deploys-per-day quantity, so no version row is inserted and no deploy is counted.",
"remedy": "Zip the project folder's contents, with package.json at the zip's root, upload the zip, and call deploy again."
},
{
"name": "ask_not_pending",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAPI-18",
"summary": "rate_experience named an ask that is not open to the acting account: already answered, declined, cancelled, or expired, or put to another account. Nothing is recorded.",
"remedy": "Read the pending ask through read_feedback and name its id, or omit ask to record an unprompted rating."
},
{
"name": "audience_mismatch",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account id_token names an audience other than the declared client.",
"remedy": "Set entra.client_id with configure_realm to the client id of the tenant app registration the sign-in uses. Then ask the end user to sign in again."
},
{
"name": "authentication_required",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"realm_surface",
"router",
"logging",
"push",
"deploy_progress"
],
"status": 401,
"owner": "MCP-02",
"summary": "No credential resolved to an account. The refusal is raised as the standing challenge naming the protected-resource metadata, at the internal resolve endpoint gate, or at the audience gate the router applies (ADM-L0-05). On the management and MCP surfaces the detail states whether the connection presented no credential or presented one that resolved to no account (MCP-02). Where the presented credential has the form of a short-lived grant and the platform serves no grant of that value, the detail says that the grant was not accepted (MAPI-03). At `deploy`'s preparing form on the HTTP action route, such a value is refused `deploy_code_refused` instead (PLD-L0-86).",
"remedy": "Where no credential was presented, reconnect with sign-in, start the OAuth flow, or present a minted token or the credential the surface takes. Where the presented credential resolved to no account, sign in again, or on an application's routes have the end user sign in again. Where a grant was not accepted, it expired and was removed, or its value was changed. Where the command or line a tool call answered carried the grant, make that call again and run the fresh command it answers. Where your application requested the grant, request another."
},
{
"name": "batch_too_large",
"surfaces": [
"logging"
],
"status": 413,
"owner": null,
"summary": "The batch body or its record count exceeds the stated bound.",
"remedy": "Split the batch into parts of at most 500 records and 512 KiB of body each, then send the parts in order."
},
{
"name": "beta_plan_limit",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACB-L0-83",
"summary": "Through the beta the account already holds its limit of live applications on the plan named: one on Standard and one on Pro (standard-application-limit and pro-application-limit). A create_application naming that plan, or a set_plan moving another application onto it, is refused: nothing is created and no plan is moved. The detail names the live application holding the slot.",
"remedy": "Move the application holding the slot to another plan with set_plan, or choose another plan for this one, then repeat the request."
},
{
"name": "binding_refused",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "EGW-L0-01",
"summary": "declare_upstream: a bound upstream is neither unbound nor re-bound to another application. On submit_manifest, another application of the account declared an entry's name after the submission's check, so that entry was not written; the manifest stays recorded, and the detail names the upstreams declared and those not.",
"remedy": "Keep the standing binding, or declare the upstream for the other application under a different name with declare_upstream. Ending the upstream with undeclare_upstream ends the binding. On submit_manifest, rename the entry and submit the manifest again before the next deploy or promote, which declares the rest.",
"members": {
"application": {
"type": "string",
"description": "The id of the application the standing upstream of that name is bound to, which is not the application this declaration named."
}
}
},
{
"name": "blueprint_required",
"surfaces": [
"management_action",
"egress",
"builder_sign_in"
],
"status": 403,
"owner": "ACB-L0-82",
"summary": "The account does not hold Turn Zero Blueprint, the `blueprint` product profile. On create_issue_space it answers every creation, with nothing created. On mint_token it answers a token asking for the issues grant, and on relay_issue_act every relayed call, whatever kind of space is named. On the egress gateway it answers a hosted application's call through its binding to a space of its account. On Turn Zero Blueprint's confirm page and at its code exchange it answers the request for one issue space's token, with nothing minted; the page's link returns it to the command.",
"remedy": "Turn Zero Blueprint is given by invitation during the private beta. Once the account holds it, repeat the request; read_account lists the products the account holds. On Turn Zero Blueprint's sign-in, run the command again once the account holds it."
},
{
"name": "bound_setting_unreadable",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "MAN-14",
"summary": "deploy, promote, roll_back, or a platform restart: a setting the manifest binds names a secret whose entry stands at the environment's scope, and its value did not answer from the store. The row ended failed before the compute apply, so the serving compute is untouched; the detail names the setting and the secret.",
"remedy": "Deploy, promote, or roll back again; the platform retries a restart at its next pass. If the refusal repeats, report it with its detail. Storing the value again with store_secret does not help while the store does not answer."
},
{
"name": "browser_session_required",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-05",
"summary": "The approval action reached other than through the approval page (MAPI-05): a bearer credential, or the browser session on the actions routes, neither of which approves.",
"remedy": "Open the approval link the destructive request returned in a browser where you are signed in, and approve or decline on that page. Afterwards, read_pending_action reports the outcome."
},
{
"name": "build_wait_exceeded",
"surfaces": [
"management_action"
],
"status": 503,
"owner": "PLD-L0-63",
"summary": "deploy: the image build waited fifteen minutes for its turn behind other image builds on the same control plane process and never started, so nothing was built or applied, and the serving version is untouched. The history row ends failed with this outcome at the image_build step.",
"remedy": "Deploy again; the new deploy takes its own turn. Where the wait repeats, the platform is busy with other builds, so wait a few minutes before deploying again."
},
{
"name": "cell_not_configured",
"surfaces": [
"management_action"
],
"status": 503,
"owner": "PLD-L0-62",
"summary": "No hosting cell is open to the act. The actions create_application, submit_manifest, deploy, and declare_storage_area answer it when the placement registry holds cells and none admits. The action create_application also answers it when no routing tier admits. The action deploy answers it when no cell is registered and no deploy configuration stands, or when the application's placement names no registered cell. The action submit_manifest answers it when the application has no placement to provision a database on. A promote or a production deploy answers it at its database_pair step, the history row ending failed, when the production environment has no placement to provision a database on. The action read_logs answers it when the cell's log workspace is not configured. The action delete_environment answers it after its approval when the development environment has no placement row and no cell or routing tier admits one, or no cell is registered (PLD-L0-62).",
"remedy": "Nothing on the caller's side corrects this. Report the refusal with its detail, and repeat the request once the platform's operator has registered an admitting cell and routing tier, or has finished configuring the cell."
},
{
"name": "cell_unavailable",
"surfaces": [
"management_action"
],
"status": 503,
"owner": "PLD-L0-62",
"summary": "No admitting hosting cell has headroom under its nominal capacity, so the application cannot be placed. The actions create_application, submit_manifest, deploy, and declare_storage_area answer it, and the action delete_environment answers it after its approval when the development environment has no placement row (PLD-L0-62).",
"remedy": "Nothing on the caller's side corrects this. Report the refusal with its detail, and repeat the request once the platform's operator has registered a cell with headroom or raised a cell's nominal capacity."
},
{
"name": "client_secret_unreadable",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account client secret did not answer from custody at the token exchange, or the Apple signing key did not answer at the client-secret mint.",
"remedy": "Store the client secret or the key again with store_secret, naming this application and the realm's environment, under the configured entra.client_secret_name or apple.key_secret_name, then ask the end user to sign in again. If the refusal repeats, report it to the platform operator, because nothing further on your side corrects it."
},
{
"name": "client_upgrade_required",
"surfaces": [
"router"
],
"status": 426,
"owner": "SVC-L0-11",
"summary": "The serving router answers this on an application request whose `x-turnzero-cloud-client` header names a native client the realm declares, at a version below that client's minimum version. The body carries `minimum_version`, the oldest version admitted, and `update_url`, the store link the client declares, null where it declares none. The request reaches no application code and counts toward no request limit.",
"remedy": "Install the app's current version from the update URL and open it again. Where the refusal was not intended, the developer lowers or removes the client's minimum_version with configure_realm on the environment's realm."
},
{
"name": "context_changed",
"status": 409,
"surfaces": [
"management_action",
"mcp_server"
],
"owner": "CTX-07",
"summary": "The supplied continuation stamp no longer matches the visible catalog or content.",
"remedy": "Repeat the request from offset zero without a stamp, then continue paging with the stamp the new response names."
},
{
"name": "context_not_found",
"status": 404,
"surfaces": [
"management_action",
"mcp_server"
],
"owner": "CTX-07",
"summary": "The content ID is absent from the currently visible fixed catalog, or a page route is absent from the tree's manifest.",
"remedy": "Call list_context and copy the identifier exactly as the catalog lists it, then repeat read_context with it. For an identifier beginning docs:, call read_documentation with the tree and part its catalog row names instead; for a page, pass its route as the tree's index prints it, which the manifest lists."
},
{
"name": "context_unavailable",
"status": 503,
"surfaces": [
"management_action",
"mcp_server"
],
"owner": "CTX-07",
"summary": "An indexed source or built documentation tree is unavailable.",
"remedy": "Nothing on the caller's side corrects this. The platform restores the tree or indexed file by its next publish or release, so retry later and report the refusal with its detail if it persists."
},
{
"name": "continue_new_removed",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 410,
"owner": "ACC-L0-04",
"summary": "The retired continue-new route: a separate account under an address an existing account holds is no longer created; the one exit is to link.",
"remedy": "Link the two accounts instead: sign in with the route the existing account already holds, or, where the page offers it, request a code to that address and type it. Start the sign-in again where the linking page has closed."
},
{
"name": "creation_contradicts_audience",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ADM-L0-05",
"summary": "configure_realm: the manifest declares the invited audience, and the call names open creation. An invited audience is invitation-only on both realms from the declaration.",
"remedy": "Leave creation out of the call, or name invited. To admit a first sign-in that carries no invitation, change the manifest's audience to public with submit_manifest first.",
"members": {
"audience": {
"type": "string",
"description": "The audience the application's manifest declares, invited at this refusal."
},
"creation": {
"type": "string",
"description": "The creation mode the call named, open at this refusal."
}
}
},
{
"name": "credential_lookup_busy",
"surfaces": [
"storage",
"egress",
"logging",
"push"
],
"status": 503,
"owner": "PLD-L0-67",
"summary": "On the storage, egress, logging, and push wires, the gateway replica could not start looking up the presented credential within its wait bound, two seconds by default, or its places for waiting lookups were full. Each replica bounds the lookups its credential cache cannot answer. The request was not processed and counts in no window.",
"remedy": "Repeat the same request unchanged after one second, the time the Retry-After header names. It was not processed, so a repeat causes no duplicate effect. A credential the gateway looked up within its cache interval, 30 seconds by default, is not looked up again."
},
{
"name": "credential_not_in_custody",
"surfaces": [
"management_action",
"egress"
],
"status": 409,
"owner": "SCRT-L0-08",
"summary": "The declared credential name is not in the account custody at the reached scope; store_secret puts it there. A name stored for the application's other environment alone is refused too, since each environment reads its own scope and the account scope. On declare_upstream, where the entry ended while the declaration was written and the write cannot be taken back, the declaration stands as written and the detail says so.",
"remedy": "Store a value under the declared credential name with store_secret, for the account or for the application's environment, then repeat the request. Where the detail names the other environment, store this environment's own value under the same name at this environment's scope of the application: each environment reads its own scope, so development can hold a test key and production a live one. A key both environments share can instead stand once at the account scope under a new name, which every upstream of the account that names it reads, with the upstream declared again naming it. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys. Where the detail says the declaration stands, declare the upstream again with a stored credential name, or store the credential again."
},
{
"name": "credential_unreadable",
"surfaces": [
"egress"
],
"status": 502,
"owner": "EGW-L0-03",
"summary": "Custody holds the name but the value read failed at the egress edge.",
"remedy": "Retry the request. If the refusal repeats, report it with its detail."
},
{
"name": "custody_entry_missing",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "configure_realm or configure_push: the named work-account client secret, Apple signing key, or push provider credential is not in custody under the application scope at the named environment. On submit_manifest, the entry of a route credential the realm member names ended after the check, so that environment's realm was not configured; the manifest stays recorded, and the detail names the realms done and those not. On create_environment, the same on development, the member not recorded there.",
"remedy": "Store the secret with store_secret, naming this application and the environment, under the name you will configure. Then call configure_realm again with that name in entra.client_secret_name or apple.key_secret_name, or configure_push again with it in apns.key_secret_name or fcm.service_account_secret_name. On submit_manifest, store the value again, or under a new name the realm member then names, and submit the manifest again. On create_environment, store the value again and call it again, or use a new name in the member and submit the manifest.",
"members": {
"client_secret_name": {
"type": "string",
"description": "The secret name the call, or the manifest's realm member, gave as the work-account client secret, the Apple signing key, or the push provider credential, for which custody holds no entry at the application's scope."
},
"application": {
"type": "string",
"description": "The id of the application whose realm the call, the submission, or create_environment configures, and at whose scope the entry was looked up."
}
}
},
{
"name": "custody_entry_unmovable",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "configure_realm: the cell's realm vault already holds the client secret's or the key's name at another version, so the value cannot move there; nothing moved and no row was written. On submit_manifest, the realm vault took the name after the check, so that environment's realm was not configured; the manifest stays recorded, and the detail names the realms done and those not. On create_environment, the same on development, the member not recorded there.",
"remedy": "Store the value under a new name at the application's scope with store_secret, then call configure_realm again with that name in entra.client_secret_name or apple.key_secret_name. On submit_manifest or create_environment, store the value under a new name, change the realm member to it, and submit the manifest again."
},
{
"name": "database_credential_unreadable",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "DBS-L0-02",
"summary": "deploy, promote, or restart: the application database marker stands but its credential does not answer from custody.",
"remedy": "Retry the request, and where it repeats for the development environment, call submit_manifest from your tool with the application, its manifest, and local_run, and run the line it answers as given. It re-mints the development database credential into custody through rotate_secret. Then deploy again. Where it repeats for production, nothing on the caller's side corrects it, and the platform operator restores the production credential in custody."
},
{
"name": "database_not_provisioned",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-63",
"summary": "deploy: the deploy goes to development, the recorded manifest declares the database kind, and the development environment has no database. That happens after delete_environment and then create_environment with no submit_manifest since, or after a submission whose database provisioning was refused. Nothing was written, and no deploy was counted toward the day's quantity.",
"remedy": "Call submit_manifest again with the same manifest, which provisions the development database, then deploy again."
},
{
"name": "database_provisioning_failed",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "PLD-L0-80",
"summary": "submit_manifest: the database role or password provisioning for the declared database kind failed. Or rotate_secret found the development database recorded and its role missing, so nothing was changed. Either failure is recorded on the platform side under a reference the detail carries, and the detail never carries the error's own message.",
"remedy": "After submit_manifest, call it again with the same manifest, because a retry completes the partial provisioning run; if that refusal repeats, report it and quote the reference its detail carries. After rotate_secret, delete_environment naming development removes the database, on one environment or two, with the secrets, files, and logs kept at the development scope. Then submit_manifest sets it up again with a new database, with create_environment before it on two environments. If that deletion fails, report it and quote the reference its detail carries."
},
{
"name": "declared_audience_contradicts_route",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ADM-L0-05",
"summary": "submit_manifest: the manifest declares the invited audience while a standing realm's sign-in methods name the work-account route, entra, which an invitation-only realm refuses.",
"remedy": "Call configure_realm for each realm whose sign-in methods name entra, naming sign_in_methods without it, then call submit_manifest again. Or keep the audience the recorded manifest declares.",
"members": {
"audience": {
"type": "string",
"description": "The audience the submitted manifest declares, invited at this refusal."
},
"environment": {
"type": "string",
"description": "The environment whose standing realm names the work-account route, development or production, the first one found."
},
"sign_in_methods": {
"type": "array",
"items": {
"type": "string"
},
"description": "The sign-in methods that realm is configured with, the work-account route entra among them."
}
}
},
{
"name": "declared_tenant_contradicts_route",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ADM-L0-05",
"summary": "submit_manifest: the manifest's workforce audience names an Entra tenant other than the one a standing realm's work-account route is configured against, in either environment's realm.",
"remedy": "Call configure_realm for the environment the refusal names, naming the tenant the manifest declares, or change the manifest's workforce tenant to the one the route is configured against. Then call submit_manifest again.",
"members": {
"tenant": {
"type": "string",
"description": "The Entra tenant the submitted manifest declares under the workforce audience."
},
"configured_tenant": {
"type": "string",
"description": "The Entra tenant the work-account route of that environment's realm is configured against."
},
"environment": {
"type": "string",
"description": "The environment whose standing realm's work-account route names another tenant, development or production, the first one found."
}
}
},
{
"name": "deletion_in_progress",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-66",
"summary": "every action whose request names an application, except the reads, `read_pending_action`, `delete_application`, and a `delete_environment` on the environment whose own row carries the marker: a deletion of the application or of one of its environments is in flight. A failed deletion walk is retried by the same deletion action, and the marker clears when the walk completes.",
"remedy": "Wait for the deletion to finish, watching it through list_applications or read_pending_action, then repeat your request only if the development environment alone was deleted, since a deleted application no longer exists. If the deletion failed, run the same delete_application or delete_environment on the same subject again to complete it."
},
{
"name": "deploy_area_unavailable",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-86",
"summary": "deploy's preparing call: a storage area the account declared stands under the name of the application's deploy area, `deploy-<application id>`, without the platform-held marker, so no upload can be prepared there. The standing area is left as it is.",
"remedy": "Deploy with `artifact` from an area of your own, uploaded under a grant from mint_upload_grant. The standing area and its files are the account's own, and a deploy leaves them untouched."
},
{
"name": "deploy_code_refused",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "PLD-L0-86",
"summary": "deploy's preparing call on the HTTP action route under a deploy code, the one-time code a line-form `deploy` call puts in its line: the code is unknown, expired, or already used, by an earlier run of the line or by another party. One refusal, alike in name, status, and detail, answers every such state and a code presented for another application, so it says nothing of whether a code existed or was run. Every call there that presents a code the platform finds spends it.",
"remedy": "Call `deploy` again and run the line it answers; its `previous_code` says what became of this code. Where `previous_code` names a started upload whose id no `prepared:` line of yours printed, roll back, rotate the application's secrets and its database credential, and report it."
},
{
"name": "deploy_failed",
"surfaces": [
"management_action"
],
"status": null,
"owner": "PLD-L0-90",
"summary": "deploy: a run the registry did not schedule, most often a build refused before it started because the platform's base image could not be read, so nothing was built or applied and the serving version is untouched. The history row ends failed with this outcome, its detail the refusal's text and no `build` member.",
"remedy": "Read the failed row's outcome through read_status or list_versions. Where its detail says a retry may go through, deploy again; where it says the platform has recorded it, nothing in the artifact needs to change, and a deploy goes through once the platform restores the image."
},
{
"name": "deploy_in_flight",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-63",
"summary": "deploy, promote, halt_environment, clear_development_database: the environment already holds a version-history row in flight. For a deploy with `artifact`, the in-flight row is a deploy whose artifact hash differs from this request's, and a request carrying the in-flight hash answers that deploy instead. For a deploy naming `upload`, the in-flight row did not read that upload: another upload is refused even where its bytes are identical, and the same upload answers that deploy instead (PLD-L0-86). A `restart` in flight (the re-creation of the serving compute under current settings by `restart_application`, a rename, or the platform) refuses a deploy whatever its hash (PLD-L0-84). A deploy to production is refused the same way while a rollback or a promote of production is in flight (PLD-L0-43; PLD-L0-96). For a promote, a production row of any kind is in flight, and its end is read through `read_status` or `list_versions`. For a halt, a deploy, promote, or restart of the environment is in flight; for a development database clear, a development deploy or restart is; and either is admitted once its row ends (PLD-L0-41; DBS-L0-10). A halt of production while a production deploy is still building its image is admitted instead, and it ends that deploy; past the build it is refused until the deploy ends (PLD-L0-41).",
"remedy": "Watch read_status or list_versions until the in-flight deploy, promote, or restart ends, then repeat the request. To follow a deploy already in flight, repeat the deploy with the same artifact or with the same upload."
},
{
"name": "deploy_seam_absent",
"surfaces": [
"management_action"
],
"status": 503,
"owner": null,
"summary": "deploy, read_status, set_plan, and a container read of read_logs: the cell is configured but no live provider seam is bound.",
"remedy": "Nothing on the caller's side corrects this. The platform operator binds the provider seam on the control plane, so report the refusal with its detail."
},
{
"name": "deploys_per_day_exceeded",
"surfaces": [
"management_action"
],
"status": 429,
"owner": "PLD-L0-63",
"summary": "deploy: the application's deploys started within the last 24 hours reach its plan's `deploys-per-day` quantity, served from the pricing registry (PRC-L0-16). The next deploy is admitted once the oldest of them is older than 24 hours; a promote is not a deploy.",
"remedy": "Wait until the application's oldest deploy of the last 24 hours is more than 24 hours old, then deploy again. On an application with two environments, promoting an already-built version stays admitted meanwhile."
},
{
"name": "description_changed",
"surfaces": [
"management_action"
],
"status": null,
"owner": "API-L0-07",
"summary": "A pending action records this outcome when the approval's own re-description of the subject differs from the one the person approved. A re-description refusing by name counts as changed. The record ends declined, and nothing executes. The outcome carries description (approved) and current_description. The outcome is read through read_pending_action.",
"remedy": "Compare the description you approved with the current one, on the approval page or through read_pending_action. Where the act is still wanted, request it again and approve the current description in the browser."
},
{
"name": "destructive_class_required",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-12",
"summary": "A destructive-tier request from a credential holding no destructive class; no pending action is created.",
"remedy": "Repeat the action from your tool's connected session, the one your own sign-in opened. Alternatively, from that session call mint_token with the destructive grant, then repeat the action under the new token."
},
{
"name": "development_realm_full",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-12",
"summary": "A sign-in that would create the next end-user account of a development realm already holding the served `development-realm-account-limit` for its plan (ten at this revision): nothing is created, an existing account still signs in, and the production realm has no such cap.",
"remedy": "Sign in with an account the development realm already holds, or ask the application's author to delete one of its end users with delete_end_user, naming the development environment. Only the platform operator raises the limit."
},
{
"name": "differing_redeclaration",
"surfaces": [
"management_action",
"storage"
],
"status": 409,
"owner": "OST-L0-01",
"summary": "An area re-declared with declarations differing from the standing ones.",
"remedy": "Send the declaration again with the standing declarations the refusal names. To use different declarations, declare a new area under another name with declare_storage_area and move the files into it, or, where the area holds no file, undeclare it with undeclare_storage_area and declare the name again."
},
{
"name": "egress_connect_failed",
"surfaces": [
"egress_tunnel"
],
"status": 502,
"owner": "EGW-L0-16",
"summary": "The tunnel seat: the pinned dial to the resolved address was not accepted.",
"remedy": "Retry the request. If the refusal repeats, report it with its detail."
},
{
"name": "egress_connections_capped",
"surfaces": [
"egress_tunnel"
],
"status": 429,
"owner": "EGW-L0-18",
"summary": "The tunnel proxy refused a new outbound connection. The application opened more connections in this UTC minute than its plan allows on this proxy replica. The body carries the count, the limit, and the instant the minute ends. Connections already open keep running.",
"remedy": "Wait for the next UTC minute, then connect again. Reuse connections instead of opening one per request. If the limit is too low for your application, move it to a larger plan with set_plan."
},
{
"name": "egress_daily_bytes_capped",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 429,
"owner": "EGW-L0-18",
"summary": "The application has moved more bytes today, in UTC, through outbound connections and calls to its own upstreams than its plan allows. The tunnel proxy refuses new connections and cuts open ones at their next byte, the cut recorded as refused_bounds. The gateway refuses calls to the application's own declared upstreams. The body carries the day's bytes, the limit, and resets_at, the first instant of the next UTC day.",
"remedy": "Wait for the instant resets_at names, the start of the next UTC day, then try again. Read today's bytes and the limit in read_usage's egress_limits member. If the limit is too low for your application, move it to a larger plan with set_plan."
},
{
"name": "egress_key_not_admitted",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"egress_tunnel",
"logging",
"documentation",
"realm_surface",
"push"
],
"status": null,
"owner": "SEC-L0-18",
"summary": "The egress key the platform mints for one upstream of one deployed compute serves that upstream's keyed route alone. It is refused by name everywhere else (403): another upstream, a management action, the storage and logging routes, a gated documentation tree's machine files, the push send route, and the realm surface. The MCP server answers it with a 401 challenge, and the tunnel seat with 407.",
"remedy": "Present the egress key only as the bearer of calls under the base URL its setting names, which the deploy set for that upstream. To call another upstream the same way, declare it with its own `settings` and read that upstream's key setting. For any other act, present the credential that surface admits, such as the application's platform credential on the storage and logging routes.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused, egress_key at this refusal."
}
}
},
{
"name": "egress_link_local_address",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-13",
"summary": "The tunnel seat: the target is, or its name resolved to, a link-local address, the instance metadata address among them, at establishment. The egress gateway at each call: the declared upstream’s host resolved to a link-local address (EGW-L0-01).",
"remedy": "Send the request to a host name that resolves to a public unicast address, and make each redirect it follows do the same. Declaring the name does not admit a link-local address. For a declared upstream, run declare_upstream again under the same upstream name with a base URL whose host resolves to public unicast addresses alone. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "egress_loopback_address",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-13",
"summary": "The tunnel seat: the target is, or its name resolved to, a loopback address at establishment. The egress gateway at each call: the declared upstream’s host resolved to a loopback address (EGW-L0-01).",
"remedy": "Send the request to a host name that resolves to a public unicast address, and make each redirect it follows do the same. Declaring the name does not admit a loopback address. For a declared upstream, run declare_upstream again under the same upstream name with a base URL whose host resolves to public unicast addresses alone. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "egress_platform_address",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-15",
"summary": "The tunnel seat: the target is a platform endpoint by name, or is, or its name resolved to, an address in the platform’s own range; no tunnel reaches it. The egress gateway at each call: the declared upstream’s host resolved to an address in the platform’s own range (EGW-L0-01).",
"remedy": "Call that endpoint directly, with no proxy agent on the request, and do not add it to your manifest’s egress list. Where your manifest does not declare the service that provides it, add the service with submit_manifest, then deploy. For a declared upstream, run declare_upstream again under the same upstream name with a base URL whose host resolves to public unicast addresses alone; no declared upstream reaches the platform’s own range. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "egress_port_refused",
"surfaces": [
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-12",
"summary": "The tunnel proxy refuses CONNECT requests naming a port other than 443 and forward HTTP requests. This applies in observe and enforce modes. Accepted CONNECT tunnels carry bytes without inspecting TLS or HTTP.",
"remedy": "Open a CONNECT tunnel to the destination on port 443. Where the destination accepts only another port, nothing on the caller's side corrects this, because only the platform can permit another port. Ports 25, 465, 587, and 2525 are outbound mail ports: applications send no mail directly; send mail through a mail provider's HTTPS API, declared as an upstream."
},
{
"name": "egress_private_address",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-13",
"summary": "The tunnel seat: the target is, or its name resolved to, a private address at establishment. The egress gateway at each call: the declared upstream’s host resolved to a private address (EGW-L0-01).",
"remedy": "Send the request to a host name that resolves to a public unicast address, and make each redirect it follows do the same. Declaring the name does not admit a private address. For a declared upstream, run declare_upstream again under the same upstream name with a base URL whose host resolves to public unicast addresses alone. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "egress_reserved_address",
"surfaces": [
"egress",
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-13",
"summary": "The tunnel seat: the target is, or its name resolved to, a reserved, unspecified, documentation, benchmarking, or multicast address at establishment. The egress gateway at each call: the declared upstream’s host resolved to an address in a reserved range (EGW-L0-01).",
"remedy": "Send the request to a host name that resolves to a public unicast address, and make each redirect it follows do the same. Declaring the name does not admit an address in a reserved range. For a declared upstream, run declare_upstream again under the same upstream name with a base URL whose host resolves to public unicast addresses alone. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "egress_resolve_unavailable",
"surfaces": [
"egress_tunnel"
],
"status": 503,
"owner": "EGW-L0-16",
"summary": "The tunnel seat: the control plane did not answer the declaration read, and no answer is held for the credential or the held answer has reached the seat's maximum authorization age. The establishment is refused rather than admitted unchecked.",
"remedy": "Retry the connection after a short wait. The refusal ends when the platform's control plane answers the tunnel proxy again, and no change on your side is needed."
},
{
"name": "egress_undeclared",
"surfaces": [
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-14",
"summary": "The tunnel seat, enforce mode: the target host is not declared in the manifest's egress member. The body carries the host and the remedy. For a hostname the remedy is the exact manifest edit. For an address literal the remedy is the fixed sentence that no literal can be declared (MAN-09) and that the hostname the address serves is the entry to declare. In observe mode the same name is recorded in the record's observed row and never sent on the wire. An address literal in a refused class reports its class in both modes, ahead of this refusal (EGW-L0-13).",
"remedy": "Add the refused hostname to the manifest's egress list and redeploy. Where the refused host is an address literal, declare the hostname the address serves instead, and redeploy."
},
{
"name": "egress_unresolvable",
"surfaces": [
"egress_tunnel"
],
"status": 403,
"owner": "EGW-L0-13",
"summary": "The tunnel seat: the CONNECT target is not host:port, or the name resolved to no address.",
"remedy": "Write the CONNECT target as host:port, with a host name that resolves at request time to a public unicast address."
},
{
"name": "email_domain_undeliverable",
"surfaces": [
"realm_surface",
"builder_sign_in",
"management_action"
],
"status": 400,
"owner": "ACS-L0-19",
"summary": "The address's domain publishes no mail server: it does not exist, it publishes a null MX, or it publishes no MX and no A or AAAA record holding a public address. An emailed-code start outside the fixture domain is refused so, and so is issue_invitation's application-less form, the one form that sends; nothing was sent, no code is pending, and no invitation was issued.",
"remedy": "Check the address for a typo and try again with the corrected address. On a sign-in page, another sign-in method also works; for a builder invitation, issue it to an address whose domain takes mail."
},
{
"name": "end_user_credential_not_admitted",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"realm_surface",
"logging",
"push"
],
"status": null,
"owner": "ACS-L0-05",
"summary": "The end-user credential the accounts service issues is refused by name on every surface but its own realm (403; a 401 challenge at the MCP server).",
"remedy": "For a management action or the MCP server, sign in as the account through your tool or use a minted token, and on the storage, logging, and egress surfaces send the application's platform credential. At the verification route, present the application's platform credential as the bearer and put the end-user session's value in the body, and act as the end user only on the realm's own account routes.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused, end_user at this refusal."
}
}
},
{
"name": "entitlement_apply_failed",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "ACB-L0-22",
"summary": "set_plan: the plan's entitlement could not be applied. That entitlement is the replica floor on the placed application's container app (PLD-L0-63) or the role's connection limit on its provisioned database (DBS-L0-04). The detail names which, with its value and, for the connection limit, the environment's role. The provider's or the driver's own message is recorded on the platform side under a reference the detail carries and is never answered. The plan stands as it was, and the retry is the same set_plan.",
"remedy": "Call set_plan again with the same plan. If the refusal repeats, report it and quote the reference its detail carries; the platform corrects the failure, and the same set_plan is the retry after that."
},
{
"name": "environment_halted",
"surfaces": [
"management_action",
"router",
"egress_tunnel",
"builder_sign_in",
"mcp_server",
"storage",
"egress",
"realm_surface",
"documentation",
"logging"
],
"status": 503,
"owner": "SVC-L0-07",
"summary": "The serving router answers this on every path of a halted environment's hostname, the reserved prefix included: the environment's developer or the platform halted it (PLD-L0-41), and `resume_environment` on the management surface ends the halt.",
"remedy": "Call resume_environment for the application and the environment, or deploy a version to the development environment, which ends its halt. An end user asks the application's developer to do so, and the refusal ends within the router's bounded interval of the resume."
},
{
"name": "environment_mismatch",
"surfaces": [
"storage",
"egress",
"logging",
"realm_surface",
"push"
],
"status": 403,
"owner": "API-L0-17",
"summary": "A platform credential fixes the request's environment as its bound one, and the request named another environment — in the x-turnzero-cloud-environment header, or in the body member on the logging ingest and the verification route. An egress key fixes its environment the same way on the keyed route.",
"remedy": "Send the request with the x-turnzero-cloud-environment header, where you send one, and the body member environment on a log batch or the verification route, agreeing with each other and with the credential's bound environment. To reach the other environment, present that environment's platform credential, or a minted token naming that environment in the header, or in the body member environment on a log batch."
},
{
"name": "environment_never_deployed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-41",
"summary": "halt_environment: the environment holds no deployed version, so there is nothing to halt.",
"remedy": "No further act is needed on an environment that has never been deployed. To halt this environment later, first put a version on it with deploy or promote, then call halt_environment again."
},
{
"name": "environment_not_created",
"surfaces": [
"management_action",
"realm_surface"
],
"status": 409,
"owner": "PLD-L0-96",
"summary": "The call names an environment the application does not have. A new application has one environment, production, so an act naming development is refused on it, and so is `promote`, which needs a development environment to promote from. `delete_environment` is the exception where a development database setup stands, whole or stopped partway, or a deletion of it stopped: the call is admitted and removes them.",
"remedy": "Name production, or call create_environment for the application to add the development environment; a deploy then goes to development, and promote moves a version to production. To put an earlier production version back without a second environment, call roll_back."
},
{
"name": "environment_required",
"surfaces": [
"storage",
"egress",
"realm_surface",
"push"
],
"status": 400,
"owner": "API-L0-17",
"summary": "A minted token or an account-wide credential named no environment in the x-turnzero-cloud-environment header on a file route, the file list, the grant mint, or a keyed egress call. On the verification route, the token or credential named no environment in the x-turnzero-cloud-environment header and none in the body member environment.",
"remedy": "Send the request again with the x-turnzero-cloud-environment header naming the environment, development or production. On the verification route, the body member environment serves in place of the header."
},
{
"name": "environment_unavailable",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-63",
"summary": "deploy: the call named `production` on an application with two environments, where a deploy goes to development and a version reaches production through `promote` alone (PLD-L0-43; PLD-L0-96). On an application with one environment a deploy goes to production itself.",
"remedy": "Deploy to the development environment, or name no environment, then promote the resulting version to production."
},
{
"name": "environment_undeclared",
"surfaces": [
"logging"
],
"status": 400,
"owner": null,
"summary": "The batch names an environment that is neither development nor production and not the local value.",
"remedy": "Set the batch's environment member to development, production, or local, then send the batch again."
},
{
"name": "environment_unsupported",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "MAN-06",
"summary": "submit_manifest: the manifest carries an environments member. An application's environments are set by create_environment and delete_environment, never by its manifest, which declares none.",
"remedy": "Remove the environments member from the manifest, then call submit_manifest again. One manifest text serves every environment the application has, so add no replacement declaration."
},
{
"name": "execution_failed",
"surfaces": [
"management_action"
],
"status": null,
"owner": "PLD-L0-80",
"summary": "The failure body a pending action records when its handler threw something other than a named refusal, or when its description threw at approval; read through read_pending_action. The failure is recorded on the platform side under a reference the detail carries, and the detail never carries the error's own message. A deletion walk's failure also names the member the walk stopped at, beside the receipts written before it (PLD-L0-66).",
"remedy": "Read the outcome through read_pending_action and check the current state, then request the action again where it is still wanted. The new request creates a new pending action that needs browser approval, and a repeated deletion runs its walk again, reporting zero removals for what is already gone."
},
{
"name": "export_not_completed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-23",
"summary": "mint_download_grant: the named export is not completed, so no download grant is minted for it. It is still running, or it failed, a running export whose heartbeat went stale among the failed.",
"remedy": "For a running export, read it with read_export until its state is completed, then call mint_download_grant again. For a failed one, call request_export again for the application and the environment, read the new export until it is completed, and name its id."
},
{
"name": "feedback_queue_bounded",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An action outside the bound, reached by a minted token holding the feedback_queue grant and no super_admin. The grant bounds its token to read_feedback and settle_feedback, whose admits marks name it, the grant decided at each handler. The rows marked access: anonymous lie outside the bound and answer the token as they answer every connection.",
"remedy": "Call the action from the owner's signed-in session, or under a token minted through mint_token without the feedback_queue grant. The admitted member names the actions the bounded token reaches.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant that bounds the credential presented."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The actions the bound admits, in the enumeration's order: the rows the grant marks and the rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and are not listed."
}
}
},
{
"name": "feedback_rate_limited",
"surfaces": [
"management_action",
"builder_sign_in"
],
"status": 429,
"owner": "MAPI-18",
"summary": "A feedback action, record_check, relay_issue_act, or create_issue_space passed a bound. One bound is the platform's own on one account's filings, ratings, and checks in a minute, and on its feedback reads, where a rating's close counts its read of the open ask. The others are the platform's cap on every account's together, one token's relayed calls in a minute, the relay's share of one space's rate, an account's space creations in a minute, and the issue service's own rate on the platform's space. The detail names which in parentheses. On the builder sign-in surface it answers Turn Zero Blueprint's code exchange where the confirmation chose a new space and its creation is refused, nothing minted.",
"remedy": "Wait for the minute to turn, then repeat the request with the same key, which the service reads as a retry and never as a second report. On Turn Zero Blueprint's sign-in, run the command again once the minute turns, or choose an existing space on the confirm page."
},
{
"name": "free_application_limit",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACB-L0-22",
"summary": "The account already holds free-application-limit live Free applications (one, the served plan quota). create_application naming Free, and set_plan to Free on a second application, refuse: nothing is created and no plan is moved. The account proceeds on Standard or Pro, or moves the existing Free application first.",
"remedy": "Name Standard or Pro instead. To keep Free, first move the account's existing Free application to another plan with set_plan, then repeat the request."
},
{
"name": "fresh_authentication_required",
"surfaces": [
"realm_surface",
"management_action"
],
"status": 403,
"owner": "ACS-L0-05",
"summary": "On the realm surface, a passkey removal or an account deletion reached without a fresh assertion made for it, or the removal of a passkey its device no longer holds or a registration outside the sign-in's offer reached without a fresh authentication (ACS-L0-05; ACS-L0-10). Under a native session, the deletion's fresh authentication is an authorization naming prompt=login whose code is exchanged at the token endpoint under the session's token as the bearer, within five minutes (ACS-L0-14). On a management action, a state-changing action reached under the browser session more than the freshness window after the sign-in that minted it (WEB-L0-16), which a page answers with a sign-in link.",
"remedy": "On the realm surface, send the passkey removal with an assertion made for that removal. For a passkey its device no longer holds, or a registration outside the sign-in's offer, reauthenticate by start/<provider>?intent=reauth&return=app, by email/start with intent=reauth, or by another passkey at passkeys/reauth, then repeat within five minutes. Request the deletion again right after a provider sign-in, an emailed code, or a passkey assertion made for it. On a native session, run an authorization with prompt=login, exchange its code at the token endpoint under the session's token as the bearer, then post the deletion again within five minutes. Under the browser session, follow the sign-in link the page shows and then repeat the action, and read_account answers the sign-in instant the window runs from."
},
{
"name": "grant_identity_fixed",
"surfaces": [
"storage"
],
"status": 400,
"owner": "OST-L0-08",
"summary": "A write under a transfer grant presented X-Acting-Identity naming an identity other than the one fixed at minting.",
"remedy": "Send the write again with X-Acting-Identity naming the identity fixed when the grant was minted. To act as another identity, mint a new grant naming it, on the mint route or in mint_upload_grant's identity argument."
},
{
"name": "grant_minter_not_admitted",
"surfaces": [
"storage"
],
"status": 403,
"owner": "OST-L0-08",
"summary": "POST /storage/v0/grants from a credential other than the application platform credential or an application-bounded minted token.",
"remedy": "Have the application's backend request the grant under its platform credential, or under a token minted with mint_token and bounded to that application. From a developer's session or an account-wide token, mint an upload grant with mint_upload_grant instead."
},
{
"name": "grant_not_held",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-14",
"summary": "mint_token: the requested grant is not held by the minting session. destructive and super_admin are each given only where the session holds it, and synthetic_seed_purge, synthetic_estate, publication, and feedback_queue only where the session holds super_admin; the issues grant needs none (MAPI-14).",
"remedy": "Call mint_token again without the grant the refusal's grant member names. No request adds a missing grant: a person's browser sign-in gives a session the destructive class, super_admin is held by the platform's own accounts alone, and synthetic_estate is minted from a session holding super_admin.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The requested grant the minting session does not itself hold."
}
}
},
{
"name": "grant_required",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-09",
"summary": "A grant-marked action reached by a credential the row does not admit, refused by the row's grant name (MAPI-09). A row admits a credential holding its grant or super_admin, and one whose bounding grant the row's admits mark names. The same name answers a credential not holding super_admin on the application-less builder form of issue_invitation, revoke_invitation, list_invitations, and configure_realm (MAPI-09; ACS-L0-08). On the queue form of read_feedback and on settle_feedback's form for the platform's own space it answers a credential holding neither feedback_queue nor super_admin (MAPI-18). On relay_issue_act it answers a credential holding no issues grant.",
"remedy": "If you meant your own application's realm, repeat issue_invitation, revoke_invitation, list_invitations, or configure_realm with the application member set; if you meant your own submissions, repeat read_feedback without queue. For relay_issue_act, mint a token with the issues grant naming the space from your signed-in session. Otherwise nothing on the caller's side corrects this: the platform operator alone reaches the action, from a session holding the grant or an account-scoped token minted from that session with the row's grant.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant the action requires and the credential does not hold."
}
}
},
{
"name": "grant_scope_refused",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-14",
"summary": "mint_token: super_admin, or a narrow grant, synthetic_seed_purge, synthetic_estate, publication, feedback_queue, or issues, requested for an application-bounded token, which carries none of them (MAPI-14; API-L0-17).",
"remedy": "Call mint_token again either with the scope set to the whole account or without super_admin and the narrow grants among the requested grants.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant requested for an application-bounded token, which carries neither super_admin nor a narrow grant."
}
}
},
{
"name": "group_full",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-62",
"summary": "deploy: the hosting cell's admitting development group holds as many environments as its nominal capacity, so the development environment cannot be placed on the pod grain there. The detail names the group and its capacity. The deploy is admitted once the capacity is raised or another development group admits placements in the cell. A cell with no admitting development group places a container app instead and is never refused this way.",
"remedy": "Nothing on the caller's side corrects this. Repeat deploy once the platform's operator has raised the capacity of the group the detail names, or has set another development group in the cell to admit."
},
{
"name": "group_kind_mismatch",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-62",
"summary": "deploy: the development environment's placement row names a group of another kind than `development`, and a development environment is placed in a development group alone; the row's group is corrected in the placement registry before the deploy is retried, and no compute act runs.",
"remedy": "Nothing on the caller's side corrects this. Report the refusal with its detail, and repeat deploy once the platform's operator has moved the environment's placement into a development group."
},
{
"name": "handoff_invalid",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-04",
"summary": "The handoff code is unknown, spent, expired, or belongs to another realm.",
"remedy": "Start the sign-in again from the application's sign-in page and let the browser follow the return to the application immediately. Do not reload or reuse a completion address."
},
{
"name": "health_gate_failed",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "PLD-L0-59",
"summary": "deploy, promote, or restart: the candidate's health path did not answer 200 within the deadline, so the candidate is deleted and the serving compute and the previous version are untouched. The history row ends failed with this outcome and a gate member: the probe ledger, the last answer, what answered, the candidate's state, and its console's last lines.",
"remedy": "Read the detail first: it opens with the likely cause where the gate's evidence shows one. Then read the failed row's outcome through read_status or list_versions: its gate member names what answered, the candidate's state, and the console's last lines; fix the health path or the startup failure and deploy again."
},
{
"name": "health_path_unserved",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-63",
"summary": "deploy: a first deploy, to an environment that serves no version, whose zip names the recorded manifest's health path in no source file. The deploy reads the path's last segment in the zip's source files, package files and documentation set aside, before any write. No version row is inserted, nothing is built, and no deploy is counted.",
"remedy": "Name the health path in the source file that serves it, where any source file passes, a comment included, and deploy the new zip. Or set the manifest's health to a path the source serves, call submit_manifest, and deploy again; under the upload form the same upload then starts."
},
{
"name": "id_token_invalid",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-14",
"summary": "The token endpoint's token exchange was given an ID token that fails verification against its issuer's published keys. Its signature, its issuer, its expiry, or its audience failed, or the client declares no audience for that issuer.",
"remedy": "Sign in again in the app so its SDK answers a fresh ID token. Declare the audience the token names on the client with configure_realm: ios.bundle_id for Apple, google_client_ids for Google."
},
{
"name": "identity_already_bound",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACB-L0-03",
"summary": "The linking write refuses a (provider, subject) that already reaches a different account of the realm: nothing bound, answered on the link_identity add leg's callback page and the interrupt's link exit, on the builder realm and on an end-user realm alike.",
"remedy": "Sign in with that provider identity to reach the account that already holds it. Where you were adding a route to your signed-in account, link a different identity through link_identity instead."
},
{
"name": "identity_collision",
"surfaces": [
"realm_surface"
],
"status": 409,
"owner": "ACS-L0-14",
"summary": "The token exchange's ID token carries a provider-verified address another user of the realm already holds under another route. Nothing was created and no session opened.",
"remedy": "Sign in through the browser flow with the existing account's own route, and link the two routes there. Either route then reaches the one account."
},
{
"name": "identity_required",
"surfaces": [
"storage"
],
"status": 400,
"owner": "OST-L0-02",
"summary": "A write (PUT, DELETE) carried no X-Acting-Identity and no grant fixes one.",
"remedy": "Send the write again with an X-Acting-Identity header that names the acting identity."
},
{
"name": "image_build_failed",
"surfaces": [
"management_action"
],
"status": 422,
"owner": "PLD-L0-90",
"summary": "deploy: the image build of the artifact ended failed, or ran past its fifteen-minute bound, so nothing was applied and the serving version is untouched. The history row ends failed with this outcome and a `build` member: the build steps' own last lines, scrubbed of addresses, header values, and tokens.",
"remedy": "Read the failed row's outcome through read_status or list_versions: its build member's output_tail names the failing step, most often the dependency install. Fix the artifact, such as its package.json or its lockfile, and deploy again."
},
{
"name": "incident_not_found",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "PLD-L0-77",
"summary": "record_incident named an incident the platform's incident record does not hold; nothing is written.",
"remedy": "Read the open incidents and the history through read_platform_status, then repeat the request with an id from that answer, or omit the incident member to open a new row."
},
{
"name": "ingest_failed",
"surfaces": [
"logging"
],
"status": 500,
"owner": "PLD-L0-80",
"summary": "The logging store did not accept the batch; the failure is recorded on the platform side under a reference the detail carries, and the detail never carries the error's own message.",
"remedy": "Nothing on the caller's side corrects this, because the platform operates the logging store and the client's later flushes deliver once it accepts again. Read the client's fallback output and the counter logging.dropped for the records the refused batch lost."
},
{
"name": "insufficient_scope",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"realm_surface",
"documentation",
"logging",
"push",
"deploy_progress"
],
"status": 403,
"owner": "MCP-02",
"summary": "The OAuth access credential is valid for this service but lacks the scope required by the protected call; the challenge states the required scope.",
"remedy": "Start the OAuth authorization again from your tool and request the scope the challenge names. Renewing the existing token does not add a scope."
},
{
"name": "internal",
"surfaces": [
"management_action",
"egress",
"builder_sign_in",
"realm_surface",
"push",
"deploy_progress",
"workflow_start"
],
"status": 500,
"owner": "PLD-L0-80",
"summary": "An unexpected error while answering. Where the detail carries a reference, the error is recorded on the platform side under that reference. The detail is a fixed sentence and never the error's own message. At Turn Zero Blueprint's code exchange, a mint that fails after the exchange created a new space names that space, which stays with no token.",
"remedy": "Retry the request. If the refusal repeats, report it and quote the reference its detail carries. On Turn Zero Blueprint's sign-in, run the command again and choose that space on the confirm page."
},
{
"name": "interrupted",
"surfaces": [
"management_action"
],
"status": null,
"owner": "API-L0-07",
"summary": "read_pending_action: the recovery sweep marked this action failed after it remained executing for longer than thirty minutes. The sweep runs at startup and every ten minutes. Inspect the current state before requesting and approving another attempt; interruption does not prove that no changes occurred.",
"remedy": "Inspect the subject's current state before requesting another attempt. Where the act is still wanted, request it again and approve the new pending action in the browser."
},
{
"name": "invalid_batch",
"surfaces": [
"logging"
],
"status": 400,
"owner": null,
"summary": "The batch is not a JSON object carrying environment, entries, and counters.",
"remedy": "Send the batch as one JSON object with the members environment, entries, and counters, in the shape the package's client forms."
},
{
"name": "invalid_client",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-15",
"summary": "The client_id a request to the authorization, token, or revocation endpoint names, or a device registration on the realm surface carries, is no native client the end-user realm declares.",
"remedy": "Declare the client on this environment's realm with configure_realm, naming its client_id and its redirect URIs, and send the request with that client_id. read_realm shows the declared clients."
},
{
"name": "invalid_client_metadata",
"surfaces": [
"builder_sign_in"
],
"status": 400,
"owner": "MCP-02",
"summary": "Dynamic client registration with no usable redirect_uris.",
"remedy": "Register again with at least one redirect URI that is an absolute HTTPS URL or an HTTP loopback URL, with no user name, password, or fragment in it. Send token_endpoint_auth_method as none, or omit it."
},
{
"name": "invalid_grant",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 400,
"owner": "MCP-02",
"summary": "A code or refresh credential is unknown, expired, unbound, mismatched or at an ended authorizing generation, or a refresh replay is outside grace; an authentic replay still ends its family when the consumed ancestor expired. A passkey offer, or a registration from the offer or the passkey page, whose sign-in generation ended by a sign-out inside its window is refused by this name too, the offer's ticket spent and no passkey written. On an end-user realm the same name refuses a native client at the token endpoint. There it names a spent, expired, or unknown code, a code not the presenting client's, a redirect URI not the code's, or a verifier that fails the challenge. It also names a refresh credential that is neither of a live session's pair, and an ID token the token exchange already accepted, presented a second time within its life. On Turn Zero Blueprint's sign-in it also answers a confirmation or an exchange whose sign-in has ended, the confirm page's link returning it to the command. The token endpoint answers it to that client's own code, its description naming /approve/blueprint/token.",
"remedy": "Start the sign-in again from your tool so that a new authorization code and refresh token are issued. Do not send the refused code or refresh token again. Where a sign-out ended a passkey offer, sign in again and add the passkey from the site's passkey page. A native app starts the sign-in again from the app, and does not present the refused code, credential, or ID token again. Turn Zero Blueprint's command is run again, and exchanges its code at /approve/blueprint/token."
},
{
"name": "invalid_redirect_uri",
"surfaces": [
"management_action",
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-15",
"summary": "A redirect URI is outside the three admitted forms: a reverse-domain custom scheme, https on one of the application's own hostnames, or loopback http. At the authorization endpoint, the URI is not one the named client declares; a presented URI matches a declared one exactly, character for character, a loopback URI's port excepted.",
"remedy": "Declare the URI in one of the three forms with configure_realm, carrying no user information and no fragment, and send the authorization request with that URI, a loopback URI on any port."
},
{
"name": "invalid_request",
"surfaces": [
"management_action",
"storage",
"builder_sign_in",
"realm_surface",
"router",
"push",
"deploy_progress",
"mcp_server",
"egress",
"workflow_start"
],
"status": 400,
"owner": null,
"summary": "Malformed or missing input, the detail naming the member, or input holding a NUL (U+0000) or an unpaired UTF-16 surrogate, the detail naming the character; the generic validation refusal of every surface. On a management action it also answers a call that names a member the action does not declare: the detail names that member, a nested one by its path, and every member declared at that place. It also answers a body the surface could not read or a path segment whose escape does not decode, in the surface's own form, naming nothing the request carried (PLD-L0-95). At Turn Zero Blueprint's request, and at the completion of its sign-in, it also answers a browser's prefetch, which holds no confirmation.",
"remedy": "Correct the member the detail names, send a member the detail lists in place of one the action does not declare, or remove the character it names, then send the request again. A refused prefetch needs nothing: the request is answered when the person opens it."
},
{
"name": "invalid_scope",
"surfaces": [
"builder_sign_in"
],
"status": 400,
"owner": "MCP-02",
"summary": "The requested OAuth scope is unknown, malformed, or broader than the recorded grant.",
"remedy": "Request only scopes the authorization-server metadata publishes, or omit the scope parameter to take the default. To widen a grant, start a new authorization from your tool rather than renewing."
},
{
"name": "invalid_target",
"surfaces": [
"builder_sign_in"
],
"status": 400,
"owner": "MCP-02",
"summary": "The supplied OAuth resource differs from the configured service or the resource recorded at authorization.",
"remedy": "Send the resource parameter exactly as the protected-resource metadata advertises it, or omit it so the configured service is selected and the recorded resource retained."
},
{
"name": "invalid_token",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"realm_surface",
"logging",
"push",
"deploy_progress"
],
"status": 401,
"owner": "MCP-02",
"summary": "A protected call presents a credential that cannot authenticate to this service; WWW-Authenticate carries the standard OAuth error. An absent credential carries no OAuth error parameter.",
"remedy": "Renew the access token with your refresh token where your tool holds one, otherwise sign in again through your tool. An application's backend presents its current platform credential or a minted token bounded to the application."
},
{
"name": "invited_realm_refuses_work_account",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "configure_realm: an invitation-only realm, by its configured creation mode or by the manifest's invited audience, names the work-account route.",
"remedy": "Call configure_realm again with entra left out of sign_in_methods, or with creation set to open so the realm admits users by membership of the tenant rather than by invitation. Under the manifest's invited audience creation stays invitation-only, so leave the route out there.",
"members": {
"creation": {
"type": "string",
"description": "The creation mode the realm would enforce after the call, invited at this refusal."
},
"audience": {
"type": "string",
"description": "The audience the application's recorded manifest declares: public, invited, or workforce."
}
}
},
{
"name": "issue_refused",
"surfaces": [
"management_action"
],
"status": null,
"owner": "MAPI-18",
"summary": "relay_issue_act's act was refused by the issue service for its content, the issue's state, a lease, or a record the act names that does not stand. The status is the service's own and the refusal member names the service's refusal.",
"remedy": "Read the refusal member against the Issue Tracking contract's refusals, correct the act's body or the issue's state it named, and relay the act again.",
"members": {
"refusal": {
"type": "string",
"description": "The issue service's own refusal name, one the Issue Tracking contract states."
}
}
},
{
"name": "issue_service_unreachable",
"surfaces": [
"management_action",
"builder_sign_in"
],
"status": 503,
"owner": "MAPI-18",
"summary": "The issue service did not answer a call the platform made for this action: the transport failed, the call passed its bound, the service answered a fault of its own or the router's quota refusal, or it refused the platform's own credential. The detail carries the cause word in parentheses. export_account answers this whole rather than an export missing its feedback member. On the builder sign-in surface it answers Turn Zero Blueprint's code exchange where the confirmation chose a new space and its creation is refused, nothing minted.",
"remedy": "Repeat the request after a short wait with the same key, which the service reads as a retry. If the refusal continues, report it with its reference through another route. On Turn Zero Blueprint's sign-in, run the command again after a short wait."
},
{
"name": "issue_tracking_application_required",
"surfaces": [
"egress"
],
"status": 403,
"owner": "EGW-L0-08",
"summary": "The platform upstream issue-tracking is reached by an application's platform credential or a minted token bounded to an application alone, because the space belongs to one application. An account-wide session or token is refused by name.",
"remedy": "Make the call under the application's own platform credential, or under a token that mint_token bounds to that one application. To read an application's reports yourself, use read_feedback naming the application's space; settle its issues with settle_feedback naming the space, or through relay_issue_act under an issues token."
},
{
"name": "issue_tracking_call_refused",
"surfaces": [
"egress"
],
"status": 403,
"owner": "EGW-L0-06",
"summary": "The platform upstream issue-tracking admits only the calls the issue tracking package's permission-level table marks as admitted through the gateway. On an application holding its own space or a space of its account, it admits only those of the level that space is reached at. `report`, the level of an application's own space for both environments, files reports and reads them and updates or settles nothing. Every other call path is refused by name before any token read, delete_space and the stored-bytes read among them.",
"remedy": "Make only the calls the issue tracking package's client makes on the gateway, within the level the application's space is reached at. The builder updates, settles, and exports the space through the management surface under an issues token. A space is deleted by the platform with its application, never by the application's own call."
},
{
"name": "issue_tracking_not_provisioned",
"surfaces": [
"egress"
],
"status": 409,
"owner": "EGW-L0-06",
"summary": "The platform upstream issue-tracking found no space token in custody for the calling environment, so the application has no issue-tracking space there. The detail names the manifest kind issue_tracking, whose declaration provisions a space.",
"remedy": "Add {\"kind\": \"issue_tracking\"} to the manifest's services and submit it with submit_manifest, which provisions the development space. The production space is provisioned at the first promote, or at a one-environment application's first production deploy. Then repeat the request."
},
{
"name": "issue_tracking_unavailable",
"surfaces": [
"egress"
],
"status": 503,
"owner": "EGW-L0-06",
"summary": "The platform upstream issue-tracking cannot carry the call. Either the estate serves no issue service, its gateways naming no service origin, or custody holds the environment's space token and its value did not answer. The detail says which, and the call reaches no service.",
"remedy": "Repeat the request after a short wait, because a custody read that failed may answer on the next call. Where the detail says the estate serves no issue service, nothing on the caller's side corrects it, so report it with its reference."
},
{
"name": "issuer_mismatch",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account id_token names an issuer other than the pinned one.",
"remedy": "Confirm with read_realm that entra.tenant is the Directory (tenant) ID of the app registration, correcting it with configure_realm where it differs, then ask the end user to sign in again. If the refusal repeats, ask the client's tenant administrator to check the registration that issues the token."
},
{
"name": "issues_bounded",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An action outside the bound, reached by a minted token holding the issues grant and no super_admin. The grant bounds its token to list_tokens and relay_issue_act, whose admits marks name it. The rows marked access: anonymous lie outside the bound and answer the token as they answer every connection.",
"remedy": "Call the action from the owner's signed-in session, or under a token minted through mint_token without the issues grant. The admitted member names the actions the bounded token reaches.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant that bounds the credential presented."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The actions the bound admits, in the enumeration's order: the rows the grant marks and the rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and are not listed."
}
}
},
{
"name": "issues_level_refused",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "relay_issue_act named an act the level of its token's issues grant does not admit: report files, follows, checks, and reads; contribute also works issues; owner reaches every act the relay carries. Below the owner level an update whose fields name restricted with any value but true is refused so too, the owner level alone lowering the mark.",
"remedy": "Name an act the admitted member lists, or mint a token at a level that admits the act from a signed-in session of the account.",
"members": {
"level": {
"type": "string",
"description": "The level of the token's issues grant."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The acts the level admits, in the relay's order."
}
}
},
{
"name": "key_revoked",
"surfaces": [
"realm_surface"
],
"status": 401,
"owner": "ACS-L0-08",
"summary": "The re-issue route: the realm key that signed the presented session token is revoked (revoke_realm_keys), so the session ends and the user signs in again.",
"remedy": "The end user signs in again from the application. No repeat of the re-issue request restores a session whose token was signed under a revoked key."
},
{
"name": "label_in_use",
"surfaces": [
"builder_sign_in"
],
"status": 409,
"owner": "MAPI-14",
"summary": "Turn Zero Blueprint's confirm page or code exchange met a token of the request's label in the chosen space that the kit's command was not issued, one mint_token minted or another client was issued. The exchange replaces only the command's own token of its label, so nothing was minted or revoked.",
"remedy": "Revoke the token that carries the label with revoke_token, as list_tokens names it, then run the command again; or choose another space on the confirm page."
},
{
"name": "level_invalid",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "MAN-03",
"summary": "submit_manifest's issue_tracking entry named a `space` and a `level` other than `report` or `contribute`: `owner`, which no deployment holds, or a word that names no level. Nothing was recorded.",
"remedy": "Name `report` or `contribute`, or leave `level` out for `report`. The builder's wider reach to a space, settling and exporting among it, is an issues token minted with mint_token, never a deployment's."
},
{
"name": "local_route_required",
"surfaces": [
"management_action",
"mcp_server"
],
"status": 409,
"owner": "SEC-L0-07",
"summary": "rotate_secret named the platform credential's or the database credential's platform-minted name on the development scope on a surface other than the HTTP wire route: the MCP tool first among them, the dashboard and a browser session besides. Those surfaces answer no platform-minted credential value (SEC-L0-07), so the re-mint was refused before any write. The same call on the wire route re-mints and answers the value once. The line a submit_manifest call naming local_run answers makes that call and writes the environment file. A store_secret, or a rotate_secret of a secret name you stored, whose value reaches the MCP surface is refused too, before any write: a secret's value travels on the HTTP route alone, never as a tool argument (MAPI-08; SCRT-L0-02). The MCP tools declare no value, so a tool call carries none: one naming no generate stores nothing and answers the command that sends the value from the developer's machine. A `deploy` call on the MCP surface naming `zip_sha256` or `withdraw` is refused too, and nothing is prepared: the turnzero-cloud command names those on the HTTP action route alone (PLD-L0-86; MAPI-08). A mint_token call on the MCP surface naming `code_verifier` is refused too, with nothing minted: the turnzero-cloud command presents it on the HTTP action route alone, answered only where the token code form is served (MAPI-23; MAPI-08).",
"remedy": "Call submit_manifest from your tool with the application, its manifest, and local_run, and run the line it answers as given. It makes the same rotate_secret call on the HTTP wire and writes the new value into your environment file. For a value of your own, call store_secret or rotate_secret from your tool naming no value, and run the command the answer returns, or command_windows on Windows: it reads the value on your machine and sends it on the HTTP wire. For `deploy`, call it again naming the application and none of `zip_sha256`, `artifact`, and `upload`, and run the command it answers, or `command_windows` on Windows.",
"members": {
"application": {
"type": "string",
"description": "The id of the application whose platform-minted development credential the call asked to re-mint."
}
}
},
{
"name": "log_capacity_reached",
"surfaces": [
"logging"
],
"status": 409,
"owner": null,
"summary": "The batch's app-source entries would carry the application environment's retained log bytes past the plan's log-retained-capacity quantity; the whole batch is refused and the refusal counted in the stream's counter logging.refused_capacity. Entries leave the store after 30 days, and purge_logs erases the stream now.",
"remedy": "Erase the environment's stream now with purge_logs, wait for entries to leave the store after 30 days, or move the application to a larger plan through set_plan. The client does not resend the refused batch and writes it to its fallback output instead."
},
{
"name": "manifest_invalid",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "MAN-12",
"summary": "submit_manifest: the manifest fails the manifest contract; violations name the failing paths. A setting name the reserved-name rule refuses is one such path (MAN-14). So is an `upstreams` entry a rule of declare_upstream refuses, the violation naming that rule's error (EGW-L0-02). deploy or promote: a setting the recorded manifest binds has a name that rule now refuses, and the detail names it.",
"remedy": "Correct the manifest at each JSON path the violations list, or at the setting the detail names, then call submit_manifest again.",
"members": {
"violations": {
"type": "array",
"items": {
"type": "string"
},
"description": "One entry per violation, each the JSON path of the failing member, a colon, and the message. The root of the document is written as a single slash."
}
}
},
{
"name": "manifest_missing",
"surfaces": [
"management_action"
],
"status": 409,
"owner": null,
"summary": "deploy: no manifest is on file for the application; submit_manifest first.",
"remedy": "Call submit_manifest for the application, then deploy again."
},
{
"name": "manifest_owned_field",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "EGW-L0-02",
"summary": "declare_upstream, configure_realm, or configure_push: the call would change a field the bound application's recorded manifest owns, an upstream its `upstreams` member names, a field its `realm` member names, or a provider its push entry names. The detail names each field. On undeclare_upstream, the recorded manifest's `upstreams` member names the upstream, so it may not end, since no submission or call ends an upstream the member names. Nothing was written.",
"remedy": "Change the member in the manifest and call submit_manifest, which records it. Or remove it from the manifest and submit the manifest; the action then changes it. For undeclare_upstream, remove the entry and submit the manifest, deploy and promote the version that no longer calls the upstream, then call undeclare_upstream again."
},
{
"name": "method_not_allowed",
"surfaces": [
"management_action",
"storage",
"router"
],
"status": 405,
"owner": "MAPI-10",
"summary": "A mutating action reached with GET, a storage route reached with a method it does not serve, or the serving domain's apex or its www name reached with anything but GET or HEAD of /.",
"remedy": "Send a mutating action with POST. On a storage route, repeat the request with the method the detail names: PUT declares an area, and a file accepts PUT, GET, or DELETE. On the serving domain's apex or its www name, send the request to the application's own hostname."
},
{
"name": "misdirected_origin",
"surfaces": [
"builder_sign_in",
"egress",
"logging",
"management_action",
"mcp_server",
"realm_surface",
"storage",
"documentation",
"push"
],
"status": 421,
"owner": "PLD-L0-67",
"summary": "The request reached a public service without the edge. Behind the platform's edge every request must carry the edge's profile identifier in its identifier header and a forwarded host and scheme equal to the configured origin (PLD-L0-67). A request that does not is refused ahead of every route. The detail names the forwarded host and scheme the origin saw. The health reads and a marked realm leg are exempt. The check is off where no edge profile identifier is configured.",
"remedy": "Send the request to the public origin, https://turnzero.ai, through the platform's edge, not to a service's own hostname. The detail names the host and scheme the service saw."
},
{
"name": "name_bound_to_push",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PSH-L0-01",
"summary": "declare_upstream or configure_realm: the credential name is a push provider credential of this application's push configuration, which serves no upstream and no realm route. At submit_manifest, deploy, or promote, a `settings` entry binds such a name, and a push provider's credential is never bound into a process (MAN-14); nothing was recorded or written.",
"remedy": "Store the upstream's, the realm route's, or the bound setting's value under another name with store_secret and declare, configure, or bind that name; a push provider's credential is the push service's alone. For a binding, call submit_manifest again, then deploy or promote."
},
{
"name": "name_bound_to_realm",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "declare_upstream or configure_push: the credential name rests in the cell's realm vault or is a realm's configured work-account client secret or Apple signing key, which serves no upstream and no push provider. At submit_manifest, deploy, or promote, a `settings` entry binds such a name, and a realm's route credential is never bound into a process (MAN-14); nothing was recorded or written.",
"remedy": "Store the upstream's, the push provider's, or the bound setting's value under another name with store_secret and declare, configure, or bind that name; a realm's client secret or signing key is the realm's alone. For a binding, call submit_manifest again, then deploy or promote."
},
{
"name": "name_bound_to_setting",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAN-14",
"summary": "configure_realm or configure_push: a setting binds the named secret, in the application's recorded manifest, in either environment's serving row, or in a deploy, promote, or restart in flight to either. A realm's route credential or a push provider's credential is never bound into a process. The detail names the setting and where it is bound. On those actions, a refusal before the write writes nothing, and one after it takes the call's credentials back, any whose read then fails staying as recorded. On submit_manifest and create_environment, a binding recorded after the check feeds a credential the realm member or the push entry names once it is recorded, so each such credential is taken back where the record changed it. A submission's manifest stays recorded, and its detail names the realms, or the push configurations, done and those not.",
"remedy": "Store the secret under another name at the application's scope with store_secret, then call configure_realm or configure_push again with that name. A running copy keeps a binding until that environment's next deploy or promote of a manifest that no longer binds the name, and an act in flight keeps it until that act ends. On submit_manifest, store the secret under another name and change the member or the entry, or remove the binding, then submit the manifest again. On create_environment, do the same and submit the manifest, or remove the binding and call create_environment again."
},
{
"name": "name_bound_to_upstream",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "configure_realm or configure_push: the named secret is the credential of an upstream declaration bound to this application, and a realm's route credential or a push provider's credential serves no upstream.",
"remedy": "Store the secret under another name at the application's scope with store_secret, then call configure_realm or configure_push again with that name; an upstream keeps its own credential name."
},
{
"name": "name_taken",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SVC-L0-07",
"summary": "create_application and rename_application: the account already holds a live application by that name.",
"remedy": "Choose a readable name that no live application of your account carries, then repeat create_application or rename_application. A held name is freed when the application that carries it is deleted or renamed."
},
{
"name": "never_deployed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": null,
"summary": "read_logs, read_counters: the named environment holds no deployed version, or a container read named an environment that holds no compute and no record from a failed first health check; a read naming local needs none.",
"remedy": "Put a version in that environment first, with deploy, or with promote for production on an application with two environments, then repeat the read. Where the detail names a version in flight, wait until read_status reports that environment's deploy state deployed, then repeat the read. Where it names a version whose deploy or promote failed, read the failure in read_status's outcome for that version instead. Where it names development's kept lines, repeat the read with environment development."
},
{
"name": "no_such_application",
"surfaces": [
"management_action",
"storage",
"logging",
"push"
],
"status": 404,
"owner": null,
"summary": "No application by that id in the acting account.",
"remedy": "Check the application id against list_applications and repeat the request with an id it answers. Where a platform credential rather than an id named the application, the application was deleted, so stop the process that presents that credential."
},
{
"name": "no_such_end_user",
"surfaces": [
"management_action"
],
"status": 404,
"owner": null,
"summary": "No end user by that identifier in the realm of the named application.",
"remedy": "Check the end user's id and the environment against list_end_users for that application, then repeat the request with an id it answers."
},
{
"name": "no_such_entry",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "LC-01",
"summary": "read_library_entry: the name is not in the served library.",
"remedy": "Call list_library to see the served entries, then repeat read_library_entry with a name from that list. If you also passed file, read the entry without file first and take the path from its file list."
},
{
"name": "no_such_file",
"surfaces": [
"storage"
],
"status": 404,
"owner": "OST-L0-07",
"summary": "No file by that name in the area, or a named-version put of an absent name; under an export's download grant, a stored file created after the export listed its files answers the same.",
"remedy": "Check the file name the detail names against the area's file listing. To create a name that does not exist yet, send the put without If-Match, or with If-None-Match: *. Under an export's download grant, call `request_export` again and download the new export, which has the application's files as they now stand."
},
{
"name": "no_such_schedule",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "SCH-L0-06",
"summary": "The application declares no schedule of that name for that environment.",
"remedy": "Read the environment's declared schedules with read_schedules and repeat the request with one of the names it lists. A schedule not in that list must be declared before it can run."
},
{
"name": "no_such_version",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "PLD-L0-43",
"summary": "promote, roll_back: the version named is not the number of a deployed version-history row of the application, or that row was retired when its environment was deleted; `list_versions` answers the rows a promote can name.",
"remedy": "Call list_versions to read the deployed version numbers the application holds, then repeat promote or roll_back with one of them."
},
{
"name": "nonce_mismatch",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account id_token nonce is not the one this leg issued.",
"remedy": "Ask the end user to start the sign-in again from the beginning, so that a new attempt issues its own nonce."
},
{
"name": "not_configured",
"surfaces": [
"router",
"workflow_start"
],
"status": 503,
"owner": null,
"summary": "The platform-internal resolve endpoint has no router resolve secret configured, or the serving router's invoke endpoint has no invoke secret configured. On the start-line route, a plane whose setting names no repository refuses every line by this name, before any read of the token (PLD-L0-76).",
"remedy": "Nothing on the caller's side corrects this. The platform operator sets the missing secret and restarts the services that read it."
},
{
"name": "not_deployed",
"surfaces": [
"router"
],
"status": 404,
"owner": "SVC-L0-07",
"summary": "The application has no deployed version to serve a shell from.",
"remedy": "Deploy a version, or on an application with two environments promote one to production, then request the hostname again. An end user asks the application's developer to do so."
},
{
"name": "not_found",
"surfaces": [
"management_action",
"realm_surface",
"push"
],
"status": 404,
"owner": "ACS-L0-17",
"summary": "The named pending action, secret, operated account, token, connection, invitation of a realm action, synthetic purge, or export is not the acting account's own or does not exist (ACS-L0-08 for the invitation; ACS-L0-11 for the connection). For clear_development_database, the named application holds no development database (DBS-L0-10). For mint_download_grant, the export's files no longer stand in its export area (API-L0-23). For the four feedback actions, the `space` named is no issue space the acting account holds, answered before any token is read (ITS-L0-03). On the realm surface, the session a revocation from the session list names is no live session of the signed-in end user (ACS-L0-17). On the device routes, the installation names no registration of the signed-in user. On the push surface, the request names a path or a method under /push/v0 other than POST /push/v0/messages. On the realm surface, the request names a path or a method under /__account/ that no realm route answers, the OpenID Connect discovery path among them (ACS-L0-04). For read_synthetic_account_state, the `account` named is an id no account stands for, under `super_admin`.",
"remedy": "Check the identifier against the listing for its kind, list_secrets, list_tokens, list_connections, list_invitations, or list_accounts, or against the id an earlier answer returned for a pending action, a purge, an export, or a seeded or first-sign-in account. Then repeat the request with an identifier the acting account holds. For the feedback actions, name a space list_issue_spaces or submit_manifest's receipt answers, or leave `space` out for the platform's own space. On the realm surface, read the session list at GET /__account/sessions and name an id it answers. For clear_development_database there is nothing to clear: a development database stands once a submitted manifest declares the database kind. For a path no realm route answers, read the realm's endpoints at /.well-known/oauth-authorization-server on the hostname, which is served where the realm declares a client."
},
{
"name": "not_yet_provisioned",
"surfaces": [
"management_action",
"mcp_server",
"builder_sign_in"
],
"status": 501,
"owner": "MAPI-10",
"summary": "An enumerated action this build or estate does not serve. Either no build serves the action, or it needs a service the estate does not run: the feedback actions and record_check need the issue service, as does submit_manifest declaring the issue_tracking kind. On Turn Zero Blueprint's confirm page and at its code exchange it answers where the management service serves no issue service, with nothing minted, and the page's link returns it to the command.",
"remedy": "Read the action's page under the Management actions reference. Where no build serves the action, call one the platform serves instead; no retry admits the call. Where the estate runs no service the call needs, Turn Zero Blueprint's sign-in among them, nothing on the caller's side corrects it until the estate serves that service."
},
{
"name": "nothing_to_promote",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-43",
"summary": "promote: the request names no version and the development environment holds no serving version, so nothing can be promoted; deploy to development first.",
"remedy": "Deploy to the development environment, then call promote again. Or call promote naming a deployed version number, which list_versions answers."
},
{
"name": "offer_cookie_required",
"surfaces": [
"builder_sign_in"
],
"status": 400,
"owner": null,
"summary": "A passkey offer route reached without the offer cookie the page set, or with another value.",
"remedy": "Answer the offer from the browser that showed the offer page, where the offer stays live. Where that browser is closed, sign in again and answer the offer there, or add the passkey later from the site's passkey page."
},
{
"name": "passkey_already_registered",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACC-08",
"summary": "The credential identifier is already registered in this realm.",
"remedy": "Sign in with the passkey that is already registered, or run the registration ceremony again with a different authenticator."
},
{
"name": "passkey_assertion_refused",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": null,
"owner": "ACC-09",
"summary": "The assertion did not verify (400 where undecodable, 401 where the signature or user handle fails).",
"remedy": "Start the passkey prompt again from the page that offered it. If a sign-in or a confirmation is refused again, use another route that page offers."
},
{
"name": "passkey_challenge_unknown",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-10",
"summary": "The challenge is unknown, expired, or issued for another realm, kind, purpose, or user.",
"remedy": "Start the ceremony again from its options step to obtain a fresh challenge. Complete it before it expires, on the same realm and for the same user and purpose."
},
{
"name": "passkey_change_closed",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACS-L0-10",
"summary": "A revert asked of a passkey change whose seventy-two-hour window has closed, or that was reverted already; nothing changed.",
"remedy": "Where the passkey the change added is not yours, remove it on the passkey page, or on an end-user realm through the remove routes, and sign out everywhere; a change reverted once is not reverted again."
},
{
"name": "passkey_change_unknown",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 404,
"owner": "ACS-L0-10",
"summary": "A revert asked of a passkey change no row of the signed-in account or user carries.",
"remedy": "Read the open changes — the passkey page on the builder realm, GET /__account/passkeys' revertible member on an end-user realm — and name one of them."
},
{
"name": "passkey_counter_regressed",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 403,
"owner": "ACC-09",
"summary": "The assertion sign count does not exceed the stored counter: a possible clone.",
"remedy": "For a sign-in or a confirmation, use another route the page offers. For a removal, prove it with a different passkey you hold."
},
{
"name": "passkey_not_sole_route",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "ACS-L0-10",
"summary": "configure_realm, or the manifest's realm member through it, named passkey without email beside it: a passkey is the emailed code's shortcut and no route on its own (ACS-L0-10).",
"remedy": "Name email beside passkey, or leave passkey out of the set. To remove email from a set that names passkey, remove passkey with it; the realm's passkeys are dormant until both return."
},
{
"name": "passkey_not_stranded",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACS-L0-10",
"summary": "A stranded removal asked of a passkey that still asserts under the current relying party; the ordinary removal, with its fresh assertion, is the route.",
"remedy": "Remove this passkey through the ordinary removal — the passkey page on the builder realm, the remove route on an end-user realm — and complete the fresh assertion that removal asks for."
},
{
"name": "passkey_origin_mismatch",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-10",
"summary": "The ceremony ran on an origin other than the relying-party origin.",
"remedy": "Run the ceremony from a page served on the realm's own sign-in host, then send the response again. For an end-user realm that host is the environment's managed hostname, and for the builder realm it is the platform's public sign-in host."
},
{
"name": "passkey_registration_refused",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 400,
"owner": "ACC-08",
"summary": "The registration did not verify or its attestation object could not be decoded.",
"remedy": "Start the registration again from your signed-in session and complete the authenticator's user verification when it prompts you. If your authenticator cannot verify you, register with one that can."
},
{
"name": "passkey_requires_email",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 409,
"owner": "ACS-L0-10",
"summary": "A passkey registration asked for an account holding no emailed-code identity, at the options route or the register route: a passkey is the emailed code's shortcut, held only by an account that signs in by code (ACS-L0-10).",
"remedy": "Sign in by the emailed code once at the address a provider sign-in of this account verified; that adds the code to the account. Then register the passkey at that sign-in's offer, or later from the platform's passkey page or an application's register route under a fresh authentication."
},
{
"name": "passkey_rp_id_mismatch",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-10",
"summary": "The authenticator data rpIdHash is not the relying-party identifier hash.",
"remedy": "Run the ceremony with the relying-party identifier the options step returned, unchanged, from a page on the realm's own sign-in host, then send the response again. If the passkey was registered under an earlier host, sign in by another route and register a new one."
},
{
"name": "passkey_unknown",
"surfaces": [
"builder_sign_in",
"realm_surface"
],
"status": 404,
"owner": "ACC-09",
"summary": "No passkey of this realm (and, for a bound act, of this user) answers the credential identifier, or its account or user no longer exists.",
"remedy": "Sign in with a passkey registered on this sign-in host, or by another route the page offers. For a removal, name a passkey this signed-in user still holds."
},
{
"name": "passkeys_not_configured",
"surfaces": [
"builder_sign_in"
],
"status": 404,
"owner": "ACS-L0-10",
"summary": "The builder realm's passkey routes while the control plane serves no passkey route: no relying-party identifier is configured, or no sender is held, since a passkey is the emailed code's shortcut (ACS-L0-10; ACS-L0-07).",
"remedy": "Nothing on the caller's side corrects this. The platform operator configures the relying-party host and the managed sender; the routes serve again once both are held."
},
{
"name": "plan_quantity_unset",
"surfaces": [
"management_action",
"egress",
"push"
],
"status": 409,
"owner": "PRC-L0-16",
"summary": "The named plan's served quantity for one of its ten enforced entries is Unset, or, on set_unlimited_plan, one of the served values the unlimited plan sets. An Unset quantity is no row, or a row with no quantity, in the served quota table. PRC-L0-02 forbids reading that quantity as zero, unlimited, or a default. create_application onto the plan, set_plan onto it, a database provisioning under it, and submit_manifest declaring a schedule under it refuse with the plan and the measure named. So do a deploy, a promote, a roll_back, and a restart_application of an application on the plan whose environment holds a database, before any version is added. An allowance call of an application on the plan (the egress surface, EGW-L0-06) and a push send of one also refuse with the plan and the measure named. The operator's placement on the unlimited plan, set_unlimited_plan, refuses where that plan's row of any entry Pro sets is absent or Unset, a served value's among them, with the plan and the measure named. A served value's own reader reads an absent row as its default or as no bound. The remedy is the operator's set_plan_quota, with the registry cell recorded.",
"remedy": "Nothing on the caller's side sets the quantity. Ask the platform operator to set the named plan's quantity for the named measure through set_plan_quota, then repeat the request.",
"members": {
"plan": {
"type": "string",
"description": "The plan whose served quantity is Unset: free, standard, or pro, or unlimited, the company's own plan, which no customer act selects yet."
},
"measure": {
"type": "string",
"description": "The registry name of the measure whose quantity is Unset for that plan, for example schedule-count-limit."
}
}
},
{
"name": "plan_schedule_conflict",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCH-L0-01",
"summary": "The schedule rows of the plan the call moves the application onto do not admit its standing declarations, each violating schedule and its bound named; resubmit the manifest within that plan's rows first, or, on set_plan, choose another plan.",
"remedy": "Resubmit the manifest through submit_manifest with schedules that fit that plan's count limit and minimum interval, then repeat the call. On set_plan, a plan whose limits admit the schedules as declared is the other way.",
"members": {
"plan": {
"type": "string",
"description": "The plan the call moves the application onto, the plan set_plan names or unlimited on set_unlimited_plan, whose schedule rows do not admit the standing declarations. Unlimited is the company's own plan, which no customer act selects yet."
},
"schedules": {
"type": "array",
"description": "One entry per conflict between a standing schedule and the target plan. The list is never empty, and one schedule appears once per measure it violates.",
"items": {
"type": "object",
"properties": {
"schedule": {
"type": "string",
"description": "The schedule's declared name."
},
"measure": {
"type": "string",
"description": "The measure violated: schedule-minimum-interval or schedule-count-limit."
},
"bound": {
"type": "integer",
"description": "The target plan's served quantity for that measure: minutes for the interval, a count for the limit."
},
"cron": {
"type": "string",
"description": "The schedule's cron expression as recorded."
},
"gap": {
"type": "integer",
"description": "The shortest gap in whole minutes between the expression's consecutive due times, on an interval entry alone."
}
}
}
}
}
},
{
"name": "platform_credential_required",
"surfaces": [
"push"
],
"status": 403,
"owner": "PSH-L0-03",
"summary": "A send ran under a session or a minted token; the send route admits the application's platform credential alone, which names the application and fixes the environment.",
"remedy": "Send from the backend under the platform credential, the value TURNZERO_CLOUD_TOKEN carries in the environment file."
},
{
"name": "platform_credential_unreadable",
"surfaces": [
"management_action"
],
"status": 502,
"owner": "SEC-L0-07",
"summary": "deploy or restart: the environment holds a standing platform credential and its value did not answer from custody, so the act is refused rather than run under a credential the platform cannot inject.",
"remedy": "For the development environment, call submit_manifest from your tool with the application, its manifest, and local_run, and run the line it answers as given. It re-mints the development platform credential into custody. Then deploy again. If the refusal repeats, report it with its detail."
},
{
"name": "platform_minted_name",
"surfaces": [
"management_action",
"egress"
],
"status": 409,
"owner": "SEC-L0-07",
"summary": "store_secret, rotate_secret, delete_secret, configure_realm, declare_upstream, or a `settings` binding at submit_manifest, deploy, or promote named a credential the platform minted for one of the account's applications (SEC-L0-07; ITS-L0-01; EGW-L0-01; MAN-14). The three are the database credential `database-<application id>`, the platform credential `credential-<application id>`, and the issue-tracking token `issue-tracking-<application id>`. It was refused before any write. On the egress surface, a call through a declaration naming one is refused before any custody read, so no declared upstream presents a value the platform minted. A platform-minted name stays the platform's to rotate, and a realm's client secret or Apple signing key is a name the author stored (ACS-L0-09). On the development scope alone, rotate_secret re-mints the first two, never under a store or a rotate grant, and refuses the issue-tracking token at every scope. The delete_secret action refuses all three at every scope, since each ends with its environment, application, or account.",
"remedy": "Give store_secret a name of your own, and name that secret in configure_realm, declare_upstream, or a manifest binding; or re-mint a development credential by running the line a submit_manifest call naming local_run answers, which calls rotate_secret on the development scope. To rotate a production credential, call promote, with rotate_database_credential true for the database credential. A call refused at the gateway passes once the upstream is declared again under a name of your own. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys.",
"members": {
"application": {
"type": "string",
"description": "The id of the account's application whose platform-minted credential name the request named."
}
}
},
{
"name": "platform_space_configure_refused",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "ITS-L0-05",
"summary": "relay_issue_act named configure on the platform's own space, under a credential at the owner level. No level admits that act there, and nothing was changed: the platform's operator configures that space.",
"remedy": "Nothing on the caller's side corrects this. Every other act the credential's level admits still reaches the space. A change to the space's configuration is made by the platform's operator.",
"members": {
"space": {
"type": "string",
"description": "The space the request named."
}
}
},
{
"name": "progress_window_ended",
"surfaces": [
"deploy_progress"
],
"status": 403,
"owner": "PLD-L0-86",
"summary": "The deploy command's progress read was made under a started upload grant outside its window, which runs until five minutes after the deploy ends and never past fifteen minutes after the start. A grant whose start was refused, or whose upload a later preparing call replaced or a later line-form call ended, has no window.",
"remedy": "Read the deploy with `read_status` from your tool, naming the application and the environment the deploy went to, with `wait_seconds` where the deploy is still running."
},
{
"name": "provider_not_enabled",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-14",
"summary": "The token exchange's ID token is Apple's or Google's, and the realm does not enable that issuer's route: apple for Apple, google for Google.",
"remedy": "The application's author names the route among the realm's sign_in_methods with configure_realm, the apple route with its apple member. read_realm shows the enabled set."
},
{
"name": "proxy_authentication_required",
"surfaces": [
"egress_tunnel"
],
"status": 407,
"owner": "EGW-L0-16",
"summary": "The tunnel seat: no proxy credential, or one that resolves to no application; the application's platform credential is the proxy credential.",
"remedy": "Send your application's platform credential in the Proxy-Authorization header on every tunnel establishment."
},
{
"name": "publication_bounded",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An action outside the bound, reached by a minted token holding the publication grant and no super_admin. The grant bounds its token to the rows it marks, publish_library and publish_public_files. The rows marked access: anonymous lie outside the bound and answer the token as they answer every connection.",
"remedy": "Call the action from the owner's signed-in session, or under a token minted through mint_token without the publication grant. The admitted member names the actions the bounded token reaches.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant that bounds the credential presented."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The actions the bound admits, in the enumeration's order: the rows the grant marks and the rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and are not listed."
}
}
},
{
"name": "publish_incomplete",
"surfaces": [
"management_action"
],
"status": 409,
"owner": null,
"summary": "publish_library commit: blobs the catalog names are not in the store. publish_public_files commit: versioned names the manifest lists are not in the container, and the refusal names the missing ones.",
"remedy": "Run `put` for each blob or file the refusal lists as missing, or that `begin` answered as lacking, then run `commit` again.",
"members": {
"missing": {
"type": "array",
"items": {
"type": "string"
},
"description": "What the commit names and the puts never wrote, never empty. For publish_library each entry is a blob's sha256. For publish_public_files each entry is a file name, or a site-relative path for the site."
}
}
},
{
"name": "publish_not_forward",
"surfaces": [
"management_action"
],
"status": 409,
"owner": null,
"summary": "publish_library commit: a source commit other than the served one whose `served_commit` is absent or stale, no longer naming the served commit. Its begin: a catalog for the served commit that differs from the one served. Both refuse the publish. publish_public_files begin or commit: the container's served version is newer than the committed one under the numeric triple comparison. For the packages container the rule is read per package: a served package's newest version is greater than the incoming one, or a served package is absent from the incoming manifest. At commit the name is also answered where the stable manifest's version moved between the read and the conditional write, so of two overlapping publishers one commits and the other writes nothing.",
"remedy": "For publish_library, read the served commit again, check the publishing commit descends from it, and commit with it as `served_commit`; publish a changed catalog from a newer commit. Where the served version or commit is newer than yours, publish again from a trunk head ahead of it, keeping every served package in the manifest. Where another publisher committed during yours, run `begin` again and then `commit` again, for the site container with the sequence `begin` now answers plus one."
},
{
"name": "published_bytes_differ",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-68",
"summary": "publish_public_files begin or put: a versioned name already stands in the container with a different sha256 in its blob metadata. The refusal names the file, because a versioned file is never rewritten once published.",
"remedy": "Bump the version, a new release, a new package version, or a new site source commit, then run the publish for that version. Do not retry the same version with different bytes.",
"members": {
"file": {
"type": "string",
"description": "The published versioned name whose recorded sha256 differs from the incoming file's. For the site it is the full versioned name, the source commit's folder included."
}
}
},
{
"name": "push_not_configured",
"surfaces": [
"push"
],
"status": 409,
"owner": "PSH-L0-03",
"summary": "A send reached an environment whose push configuration names no provider.",
"remedy": "Store the provider credential with store_secret naming the application and the environment, then call configure_push naming it, and send again."
},
{
"name": "push_not_declared",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PSH-L0-01",
"summary": "configure_push or read_push named an application whose recorded manifest declares no push service.",
"remedy": "Add {\"kind\": \"push\"} to the manifest's services and resubmit it with submit_manifest, then repeat the request."
},
{
"name": "rate_capped",
"surfaces": [
"management_action",
"realm_surface",
"builder_sign_in",
"storage",
"egress",
"router",
"logging",
"push",
"deploy_progress",
"workflow_start",
"mcp_server",
"documentation"
],
"status": 429,
"owner": "PLD-L0-67",
"summary": "The source sent more requests in the window than the stated bound: an application's logging batches per minute, a source address's client registrations per hour, or a source address's requests per minute to the control plane or on router resolve misses (the admission window). Every request to the control plane counts once by its source address. A page view of the site counts in a page window of its own, six hundred a minute. A call to list_library or read_library_entry on the actions route counts in a library window of its own, three thousand a minute. Every other request counts in the source window, six hundred a minute. A signed-in arrival at the approval page or a dashboard page is not counted. On the storage, egress, logging, and push wires, a request whose presented credential resolves counts in a window keyed on that credential's identity and not on the source address. A presented value there that resolves to no credential counts in a window of its own for the source, six hundred a minute, apart from the source window. On those wires, a request through the edge whose source holds that bound is refused before its credential is looked up, unless the gateway already holds that credential. On the deploy command's progress read, a read under its upload's started grant counts in a window keyed on that grant's identity. A read there that presents anything else counts in the source window, which once full refuses the source before any lookup. The admission window's refusal at the control plane carries Retry-After, the seconds to the next minute. The serving router also answers it to a source past its bound of requests per minute to one application on one router replica (SVC-L0-18). That refusal comes before the request reaches the application, and its Retry-After carries the seconds to the next minute.",
"remedy": "Wait for the window to pass, the seconds Retry-After names where the response carries it, then repeat the request at a rate under the bound. On Turn Zero Blueprint's confirm page, nothing reaches the command: run it again once the minute passes. The window is one minute for requests and logging batches and one hour for client registrations."
},
{
"name": "rating_not_admitted",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-18",
"summary": "rate_experience named the human series from an account carrying the synthetic flag, the company's own test fixture, which is never asked and whose rating would count as a person's (ACB-L0-79). Nothing is recorded.",
"remedy": "File the agent series instead, or rate from a builder's own account."
},
{
"name": "realm_creation_ceiling",
"surfaces": [
"realm_surface",
"builder_sign_in"
],
"status": 403,
"owner": "ACS-L0-07",
"summary": "The realm admits no further accounts: the creation ceiling is reached. On the platform's own builder sign-in the name is recorded on the operator's side, and the person's page shows the operator's paused panel and no name.",
"remedy": "Nothing on the caller's side corrects this. The application's author raises the ceiling with configure_realm (limits.creation_ceiling), and on the platform's own builder sign-in the operator raises or clears it the same way."
},
{
"name": "realm_keys_unready",
"surfaces": [
"realm_surface"
],
"status": 503,
"owner": "PLD-L0-67",
"summary": "The re-issue route on an accounts instance whose realm key-encryption key is not unwrapped yet; the caller retries.",
"remedy": "Retry the request. If the refusal repeats, report it with its detail."
},
{
"name": "realm_not_declared",
"surfaces": [
"management_action",
"realm_surface",
"push"
],
"status": 404,
"owner": "MAN-03",
"summary": "The application declares no accounts kind, or no application declaring one carries the forwarded host; and, on the builder form of a realm action, the builder realm row absent from the store — an estate ahead of migration 0022 (ACS-L0-01). On submit_manifest, a realm ended between the submission's check and its record, so it was not configured; the manifest stays recorded, and the detail names the realms done and those not. On create_environment, development's realm ended while the act recorded the realm member.",
"remedy": "Add {\"kind\": \"accounts\"} to the manifest's services and resubmit it with submit_manifest, then repeat the request. On the builder-realm form, where the platform's own schema migration alone creates the builder realm, nothing on the caller's side corrects this. On submit_manifest, submit the manifest again, which configures each realm the application has. On create_environment, call it again."
},
{
"name": "realm_state_required",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-04",
"summary": "A handoff redeemed in a browser presenting no state cookie for the sign-in that started.",
"remedy": "Start the sign-in again from the application's sign-in page and complete it in that same browser without delay."
},
{
"name": "realm_surface_unmarked",
"surfaces": [
"realm_surface"
],
"status": 404,
"owner": "ACS-L0-04",
"summary": "The realm surface answers the serving router marked leg alone.",
"remedy": "Send the request to the application's own hostname under the /__account/ prefix, so the serving router forwards it. No header the caller adds marks the leg."
},
{
"name": "realm_vault_unregistered",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ACS-L0-09",
"summary": "configure_realm: the application's cell registers no realm vault, so the client secret or the Apple signing key has no home to move into.",
"remedy": "Report it to the platform operator, whose register write fills the cell's row; nothing on your side corrects it."
},
{
"name": "reauthentication_not_fresh",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-05",
"summary": "A provider leg started for the fresh authentication came back from a provider that reports the person last signed in with it longer ago than the five-minute window, so it proves no fresh act of theirs (ACS-L0-05). Nothing was signed in.",
"remedy": "Have the person sign in to the provider again, then start the reauthentication once more. The emailed code or a passkey assertion also makes the fresh authentication."
},
{
"name": "reauthentication_other_account",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-05",
"summary": "A reauthentication completed for an identity that resolves to a user other than the one the starting session named, or to none (ACS-L0-05). Nothing was signed in and no user was created.",
"remedy": "Start the reauthentication again under the person's own session and choose the same account at the provider as the one signed in to the application."
},
{
"name": "refresh_reused",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-14",
"summary": "A refresh credential the token endpoint replaced more than sixty seconds ago was presented again, so the native session is ended as the stolen-copy precaution: its row ended and its revocation written together.",
"remedy": "Sign in again from the app. Keep one refresh credential per installed app, replace it with each answer, and never copy it between devices or processes."
},
{
"name": "refused_base_url",
"surfaces": [
"egress"
],
"status": 400,
"owner": "EGW-L0-08",
"summary": "The declared upstream base URL is refused (scheme, host, address class, or an outbound mail port); re-declare the upstream.",
"remedy": "Correct the base URL to an https address on a public host, then run declare_upstream again under the same upstream name. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys. A base URL on an outbound mail port (25, 465, 587, or 2525) is refused as well: send mail through a mail provider's HTTPS API, declared as an upstream."
},
{
"name": "refused_platform_host",
"surfaces": [
"management_action",
"egress"
],
"status": 400,
"owner": "EGW-L0-01",
"summary": "declare_upstream, and the egress gateway at each call: the base URL's host is one of the platform's own, which no declared upstream reaches. The platform's own hosts are its vaults, its storage accounts, its container registries, and its own service hostnames, and the management and sign-in endpoints of the provider the platform runs on. The detail names the host. The refusal is by hostname and never by a provider's domain, so the caller's own vault, storage account, or registry at the same provider is admitted.",
"remedy": "Declare the upstream against a host of your own, then run declare_upstream again under the same upstream name. No declaration reaches one of the platform's own hosts, and nothing on the caller's side changes that. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys."
},
{
"name": "region_unavailable",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-22",
"summary": "submit_manifest: the region is not usa; the usa region alone is offered at the beta, so europe, uk, and global are refused by name.",
"remedy": "Set the manifest's region to usa, then call submit_manifest again. Nothing on the caller's side makes another region available, because the platform alone admits a new region to the set it serves.",
"members": {
"region": {
"type": "string",
"description": "The region the submitted manifest declares, one the platform does not offer yet."
}
}
},
{
"name": "request_too_large",
"surfaces": [
"storage",
"egress",
"builder_sign_in",
"management_action",
"mcp_server",
"realm_surface",
"push",
"router",
"workflow_start"
],
"status": 413,
"owner": "EGW-L0-05",
"summary": "The request exceeds the surface request bound, or the bound a transfer grant admits (OST-L0-04 on storage); on the builder sign-in, a client registration whose declared body exceeds 16 KiB (PLD-L0-67). On every surface, the serving router among them, it also answers a body over the bound the surface's parser reads, the detail naming that bound (PLD-L0-95).",
"remedy": "Reduce the request body to the byte bound the refusal detail names, then send it again. Keep a storage upload within the size its transfer grant admits, and keep a client registration on sign-in at or under 16 KiB."
},
{
"name": "reserved_upstream_name",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "EGW-L0-01",
"summary": "declare_upstream names a reserved upstream, ai-allowance or issue-tracking, which the platform holds and no account declares; choose another name.",
"remedy": "Declare the upstream under another name with declare_upstream. To use the included AI allowance, call the platform upstream ai-allowance without declaring it. To reach the application's issue-tracking space, call the platform upstream issue-tracking without declaring it."
},
{
"name": "response_too_large",
"surfaces": [
"egress"
],
"status": 502,
"owner": "EGW-L0-05",
"summary": "The upstream answer exceeds the response bound; a stream is cut at the crossing chunk with this terminal event.",
"remedy": "Request a smaller answer from the upstream, paging where it offers paging."
},
{
"name": "retired_host",
"surfaces": [
"builder_sign_in",
"egress",
"logging",
"management_action",
"mcp_server",
"realm_surface",
"storage",
"documentation",
"push"
],
"status": 421,
"owner": null,
"summary": "The request's hostname is one the plane retired (the public address moved to turnzero.ai, 2026-09-04): refused ahead of every route, the detail naming the current address, so a client still holding the old name fails identifiably rather than working quietly.",
"remedy": "Change the address your client holds to the current address the detail names, then send the request again."
},
{
"name": "rotation_in_flight",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "DBS-L0-02",
"summary": "rotate_secret re-minting the development database credential waited for another re-mint of the same role, which held the role's lock on the cell server past the wait the platform allows, so nothing was changed: the role keeps its password and custody its value.",
"remedy": "Wait for the other rotate_secret call to answer, then call rotate_secret again. Each call answers its own value, and the value of the call that ends last is the one the role and custody hold, so a fresh line from a submit_manifest call naming local_run writes the value that stands.",
"members": {
"application": {
"type": "string",
"description": "The id of the application whose development database credential the call asked to re-mint."
}
}
},
{
"name": "route_not_enabled",
"surfaces": [
"realm_surface"
],
"status": 400,
"owner": "ACS-L0-07",
"summary": "The named route is not in the realm effective set, or its provider is not configured on this server.",
"remedy": "Sign in through a route the realm has enabled. The application's author enables a route with configure_realm (read_realm shows the enabled set), and the operator configures a provider absent from the server."
},
{
"name": "route_set_contradicts_audience",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "ADM-L0-05",
"summary": "configure_realm: a workforce realm named a passwordless route, or an Entra tenant other than the declared one.",
"remedy": "Call configure_realm again naming only the work-account route, entra, with the tenant the manifest declares. To admit a passwordless route or another tenant, change the manifest's audience or its declared tenant with submit_manifest first.",
"members": {
"audience": {
"type": "string",
"description": "The audience the application's recorded manifest declares, workforce at this refusal."
},
"tenant": {
"type": "string",
"description": "The Entra tenant the manifest declares, present only where the call named a different tenant."
}
}
},
{
"name": "router_mark_required",
"surfaces": [
"harness"
],
"status": 403,
"owner": "HST-L0-01",
"summary": "The runtime harness's inbound guard: a request on the application's provider default hostname carries no router mark, or one the container does not hold — the intra-cell closure (SVC-L0-07); the managed hostname through the serving router is the way in.",
"remedy": "Send the request to the application's managed hostname on ai.host instead of the provider default hostname. An application calling itself from inside its own container should use the loopback address."
},
{
"name": "run_in_flight",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCH-L0-06",
"summary": "A run of the schedule is still running; a schedule holds one run in flight, and a due time during it is skipped rather than queued.",
"remedy": "Wait until read_schedules shows no run in flight for the schedule, then call run_schedule again."
},
{
"name": "schedule_count_over_plan",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCH-L0-01",
"summary": "The manifest declares more schedules than the application's plan admits — the plan's `schedule-count-limit` row — named with the first declaration past the count.",
"remedy": "Remove schedule declarations from the manifest until the count is within the plan's limit, then call submit_manifest again. Otherwise move the application through set_plan to a plan whose limit admits the count, then resubmit.",
"members": {
"path": {
"type": "string",
"description": "The JSON path of the first schedule declaration past the plan's count."
},
"plan": {
"type": "string",
"description": "The application's plan: free, standard, or pro, or unlimited, the company's own plan, which no customer act selects yet."
},
"measure": {
"type": "string",
"description": "The measure the refusal is keyed on, schedule-count-limit."
},
"quantity": {
"type": "integer",
"description": "The plan's served count limit, the number of schedules an application on the plan declares at most."
}
}
},
{
"name": "schedule_interval_below_plan",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCH-L0-01",
"summary": "A declared schedule's consecutive due times fall closer than the application's plan admits — the plan's `schedule-minimum-interval` row — named with the declaration's path and the floor; lengthen the expression or move the application to a plan whose floor admits it.",
"remedy": "Lengthen the named schedule's cron expression to meet the plan's minimum interval, then call submit_manifest again. Otherwise move the application through set_plan to a plan whose minimum interval admits the expression, then resubmit.",
"members": {
"path": {
"type": "string",
"description": "The JSON path of the cron expression whose due times fall too close together."
},
"plan": {
"type": "string",
"description": "The application's plan: free, standard, or pro, or unlimited, the company's own plan, which no customer act selects yet."
},
"measure": {
"type": "string",
"description": "The measure the refusal is keyed on, schedule-minimum-interval."
},
"quantity": {
"type": "integer",
"description": "The plan's served minimum interval in minutes, the floor."
},
"gap": {
"type": "integer",
"description": "The shortest gap in whole minutes between the expression's consecutive due times, less than the floor."
}
}
},
{
"name": "schedule_not_deployed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCH-L0-06",
"summary": "The environment holds no version deployed or promoted at or after the declaration, so the schedule cannot fire there; deploy to it, or promote to production on an application with two environments, first.",
"remedy": "Deploy to that environment, or promote to production on an application with two environments, then call run_schedule again. read_schedules shows whether each schedule still awaits a deploy."
},
{
"name": "scheduled_handler_only",
"surfaces": [
"harness"
],
"status": 404,
"owner": "HST-L0-06",
"summary": "The path is a declared scheduled handler and the request carries no invocation header the serving router set: a declared path receives the platform's scheduled runs alone, and the harness answers before the application's listener runs, recording the refusal as a harness_refusal line.",
"remedy": "Nothing on the caller's side corrects this. The application's owner makes the path public by resubmitting the manifest without that schedule through submit_manifest and then deploying or promoting the environment again."
},
{
"name": "scope_fixed",
"surfaces": [
"management_action"
],
"status": 409,
"owner": null,
"summary": "store_secret or rotate_secret named a scope the name may not share with the one it stands at: the account scope for a name at an application's scope, another application's scope, or an application's scope for a name at the account scope. An application's two environment scopes are the exception, each holding the name with its own value (SCRT-L0-08).",
"remedy": "Repeat the call naming the scope the refusal's scope, application, and environment members state, or store the value under a new name at the scope you want.",
"members": {
"scope": {
"type": "string",
"description": "The kind of scope the name stands at: account or application."
},
"application": {
"type": [
"string",
"null"
],
"description": "The id of the application whose scope the name stands at, null where it stands at the account scope."
},
"environment": {
"type": [
"string",
"null"
],
"description": "The environment of that application scope, development or production, null where the name stands at the account scope."
}
}
},
{
"name": "secret_count_limit",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SEC-L0-21",
"summary": "store_secret would add a name to an environment scope of an application that already holds 100 names, counting every name stored at that scope, the platform's own among them. Nothing was written, no grant was minted, and a grant the call presented stays unspent.",
"remedy": "Delete a name no longer needed there with delete_secret, once nothing uses it, then store again. A re-supply or a rotation of a name that stands there is never refused."
},
{
"name": "secret_exists",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SEC-L0-20",
"summary": "store_secret named generate for a name that already stands at that scope, whether its value was supplied or created. A call naming generate never replaces a value, so nothing was written.",
"remedy": "To replace a created value, store a new name with generate, bind the setting to it, deploy, then delete the old name with delete_secret. To supply a value of your own under the standing name, call store_secret naming no generate."
},
{
"name": "secret_grant_expired",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-03",
"summary": "The secret grant passed its expiry before its one write was made, so nothing was written. The grant a `submit_manifest` call naming `local_run` mints expires the same way: a `rotate_secret` request under it after its expiry re-mints nothing.",
"remedy": "Call `store_secret` or `rotate_secret` from your tool again naming no value, and run the command it answers before the expiry it states. For the local run's line, call `submit_manifest` from your tool with the application, its manifest, and `local_run`, and run the line it answers as given.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused: secret_grant."
}
}
},
{
"name": "secret_grant_not_admitted",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"logging",
"documentation",
"realm_surface",
"push"
],
"status": null,
"owner": "MAPI-03",
"summary": "The secret grant a `store_secret` or `rotate_secret` call naming no value mints serves the one write it records: the same action on the HTTP action route, naming the grant's own name, application, and environment. The grant a `submit_manifest` call naming `local_run` mints serves two requests: `rotate_secret` on that route, naming no value, for the application's database credential and its platform credential at the development scope, each once. Every other surface, every other management action, and every other request under either grant is refused by this name (403; a 401 challenge at the MCP server) and uses nothing, but for an action another rule answers first. The browser-only action and the library's anonymous reads read no credential, and an action switched off reads the grant and refuses by its switch's name, and none admits the grant. The deploy command's progress read refuses it under that read's own name, `transfer_grant_not_admitted`.",
"remedy": "Run the command the preparing call answered once, as given: it makes the one write the grant admits. For any other act, present the credential that surface admits, for example a signed-in session or a minted token on the management surface. To write another name or at another scope, call `store_secret` or `rotate_secret` naming no value for that name and scope, and run the command it answers. For the local run's grant, run the line the `submit_manifest` call answered, as given. A `submit_manifest` call naming `local_run` answers a fresh line.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused: secret_grant."
}
}
},
{
"name": "secret_grant_spent",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-03",
"summary": "The secret grant's one use was already taken. A grant serves one write, so a write under a spent grant is refused and writes nothing. `list_secrets` shows when the name was last written. Where the refused write is the command's first run, another holder of the grant took that use, and the value in custody may not be yours. The grant a `submit_manifest` call naming `local_run` mints re-mints each of the two development credentials once. The platform credential's re-mint spends it, and a second re-mint of the database credential under it is refused by this name too. Where the refused line is the command's first run, another holder of the grant made that re-mint.",
"remedy": "Do not run the command again. Where `list_secrets` shows no write at the time the command first ran, or that first run was refused this way, call `store_secret` or `rotate_secret` from your tool again naming no value. Run the command it answers, which replaces the value under that name. For the local run's grant, call `submit_manifest` from your tool with the application, its manifest, and `local_run`, and run the line it answers as given: it re-mints both credentials, which ends the values an earlier re-mint answered.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused: secret_grant."
}
}
},
{
"name": "secret_in_use",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "SCRT-L0-07",
"summary": "delete_secret: something still reads the named secret, so its value may not end. For an application-scope name, a binding feeds it, in the recorded manifest, or in the serving row of the environment whose scope holds it or a deploy, promote, or restart in flight to that environment. Or an upstream declaration of the application names it as its key, or the realm or the push configuration of the environment whose scope holds it names it now as a route credential. A route of the other environment and a value resting in the cell's realm vault after its realm came to name another are no use, and the deletion ends that resting copy. An account-scope name is in use only where an upstream declaration of any of the account's applications names it, since no binding and no realm or push route reads the account scope. The detail names each use. The request is refused before any pending action, and a use made after the approval ends the pending action failed under this name. Nothing was removed.",
"remedy": "End each use the detail names, then call delete_secret again. Remove a binding from the manifest's settings, call submit_manifest, and deploy or promote each environment whose running copy carries it, once any act in flight that carries it has ended. Point an upstream, a realm route, or a push configuration at another stored name with declare_upstream, configure_realm, or configure_push, or end an upstream the application no longer calls with undeclare_upstream."
},
{
"name": "server_unavailable",
"surfaces": [
"management_action"
],
"status": 503,
"owner": "PLD-L0-62",
"summary": "submit_manifest, promote, or deploy to production: no admitting server of the application's hosting cell holds fewer than 2,000 databases under 70 percent of its storage, so the database cannot be provisioned. Or an earlier run of the provisioning recorded a server that no longer admits, so the run cannot move to another server until that earlier run is removed. On a promote or a production deploy the history row ends failed with this outcome at its database_pair step.",
"remedy": "On submit_manifest, where the detail names an earlier run, repeat submit_manifest once, since that run may still be completing. If it repeats, delete_environment naming development removes the run, on one environment or two, with the secrets, files, and logs kept at the development scope. On two environments create_environment follows it, and a resubmission then sets the database up again. Where the detail names no earlier run, or that deletion fails, report the refusal with its detail. Repeat submit_manifest once the platform's operator has added a database server to the cell, or has removed the earlier run or set its server admitting again. On a promote or a production deploy whose detail names an earlier run, report the refusal with its detail. The platform's operator removes that run or sets its server admitting again, and the next promote or deploy then goes through. Where it names none, repeat the act once a server admits."
},
{
"name": "session_credential_required",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-14",
"summary": "mint_token is callable by the session credential alone.",
"remedy": "Under a minted token, no new token is needed for the storage routes, the keyed upstreams, and the action routes within its scope: the token presented already serves them. The logging routes and the platform upstream take a token bounded to an application, or its platform credential. Otherwise, sign in through your tool and call mint_token from that signed-in session. A token nearing its expiry is replaced by minting another from the signed-in session."
},
{
"name": "session_ended",
"surfaces": [
"realm_surface"
],
"status": 401,
"owner": "ACS-L0-06",
"summary": "No session is held under the presented value, its user or realm no longer resolves, or the session token fails verification under the realm's keys.",
"remedy": "Have the end user sign in again; a new sign-in opens a new session. Where your backend caches verdicts, hold this refusal for no more than ten seconds."
},
{
"name": "session_expired",
"surfaces": [
"realm_surface"
],
"status": 401,
"owner": "ACS-L0-06",
"summary": "The session passed its expiry.",
"remedy": "Have the end user sign in again; a new sign-in opens a new session. Where your backend caches verdicts, hold this refusal for no more than ten seconds."
},
{
"name": "session_other_account",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-06",
"summary": "verify: the realm belongs to an account other than the credential account.",
"remedy": "Verify with a credential of the account that owns the realm's application: its account-wide credential or a token minted for that application, the request naming the realm's environment. The application's own platform credential also serves."
},
{
"name": "session_other_realm",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-06",
"summary": "verify: the session belongs to a realm other than the caller application.",
"remedy": "Verify the session through the application environment whose realm holds it: present that environment's platform credential, or, from an owning-account script, name that environment in the request. Otherwise have the end user sign in to this application."
},
{
"name": "session_required",
"surfaces": [
"realm_surface"
],
"status": 401,
"owner": "ACS-L0-06",
"summary": "No end-user session cookie was presented on a route that needs one.",
"remedy": "Send the request with the end user's session cookie, which this application's sign-in set, or present that cookie's value as the bearer credential. An end user who holds no session signs in first."
},
{
"name": "session_revoked",
"surfaces": [
"realm_surface"
],
"status": 401,
"owner": "ACS-L0-06",
"summary": "The session was signed out, every session of the user ended, or, on the verification route, the realm key that signed the session token was revoked by revoke_realm_keys.",
"remedy": "Have the end user sign in again; a new sign-in opens a new session. Where your backend caches verdicts, hold this refusal for no more than ten seconds."
},
{
"name": "setting_is_upstream_key",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAN-14",
"summary": "submit_manifest, deploy, or promote: a `settings` entry binds a secret that an upstream declaration of the application names as its key. The egress gateway applies that key at its edge and never gives it to the application (EGW-L0-03), so no binding names it; nothing was recorded or written.",
"remedy": "Call the upstream through the egress gateway instead of reading its key, or store the value the code reads under another name and bind that name. Then call submit_manifest again, and deploy or promote again where the refusal came from one."
},
{
"name": "setting_scope_refused",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAN-14",
"summary": "submit_manifest: a `settings` entry binds a secret that stands at the account scope or at another application's scope, where no deploy of this application reads it (SCRT-L0-08). A value stored at the account scope is applied only to a declared upstream's calls, and a name never moves between scopes; nothing was recorded.",
"remedy": "Store the value under a new name with store_secret, naming this application and each environment, bind that name in the manifest's settings, and call submit_manifest again."
},
{
"name": "setting_secret_missing",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAN-14",
"summary": "deploy or promote: a setting the manifest binds names a secret that stands at no entry of the environment's scope of the application; the detail names the setting and the secret, and nothing was written. A deploy or promote whose bound name lost its entry after it started ends its row failed under the same name; a value whose entry stands and whose store does not answer is `bound_setting_unreadable`.",
"remedy": "Store the value with store_secret naming the application and that environment, then deploy or promote again. Or remove the binding from the manifest's settings, call submit_manifest, and deploy or promote again."
},
{
"name": "sign_in_failed",
"surfaces": [
"builder_sign_in"
],
"status": 400,
"owner": "MCP-02",
"summary": "The provider sign-in could not be verified; start over from the tool.",
"remedy": "Start the sign-in over from your tool."
},
{
"name": "sign_in_required",
"surfaces": [
"builder_sign_in"
],
"status": 401,
"owner": "MCP-02",
"summary": "No provider route is configured for the authorization, or no signed-in browser session reached a passkey management route.",
"remedy": "For a passkey route, sign in again in the browser, then return to the passkey page. Where no provider route is configured on the server, nothing on the caller's side corrects this until the platform configures one."
},
{
"name": "signin_code_invalid",
"surfaces": [
"realm_surface",
"builder_sign_in"
],
"status": 400,
"owner": "ACS-L0-12",
"summary": "A wrong, expired, superseded, or unbound sign-in code, disclosing nothing of which; the attempt is spent and the sixth ends the code.",
"remedy": "Enter the code again from the browser that asked for it. If the code has expired or its attempts are spent, start the sign-in again from that browser to receive a new code."
},
{
"name": "signin_code_rate_limited",
"surfaces": [
"realm_surface",
"builder_sign_in"
],
"status": 429,
"owner": "ACS-L0-12",
"summary": "An emailed-code start past the per-address send rate, the address's failure count for the hour, or the per-realm or estate-wide send ceiling.",
"remedy": "Wait for the hour to pass, then start the sign-in again, because requesting another code sooner does not reset the count. On an end-user realm, the application's author can raise the per-address send rate with configure_realm."
},
{
"name": "signin_rate_limited",
"surfaces": [
"realm_surface",
"builder_sign_in"
],
"status": 429,
"owner": "ACS-L0-07",
"summary": "A sign-in start past a per-source rate: an end-user realm's provider or emailed-code start, the builder realm's per-source window on emailed-code starts, or one network source's share of emailed-code starts an hour across every realm. That share is a sixth of the estate-wide ceiling as computed from the sender quota the estate holds, its number in detail (ACS-L0-12).",
"remedy": "Wait until the hour's window passes, or start the sign-in from another network. On an application's realm the author can raise the per-source rate with configure_realm (limits.signin_starts_per_hour). The builder realm's rate is fixed, and the share of emailed-code starts an hour from one network source, across every realm, is a sixth of the estate-wide ceiling, which no act of an author raises; the refusal's detail names the number."
},
{
"name": "slot_busy",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-63",
"summary": "deploy, promote, or restart: the environment's previous compute could not be torn down after the routers' interval, or its other container-app slot still stood when the wait for its absence ended, so nothing was applied; the history row ends failed with this outcome.",
"remedy": "Deploy or promote again; the retry runs the teardown and the wait again and deletes what stands under the slot. Where it repeats, read the environment's state through read_status and the platform events through read_logs."
},
{
"name": "space_creation_ceiling",
"surfaces": [
"management_action",
"builder_sign_in"
],
"status": 403,
"owner": "MAPI-18",
"summary": "The space creation would take the account past the fifty spaces of its own it may hold at once, and nothing was created. A repeat naming a space the account already holds is answered as it stands, whatever the count. On the builder sign-in surface it answers Turn Zero Blueprint's code exchange where the confirmation chose a new space and its creation is refused, nothing minted. The confirm page answers it too, from a read, where the account already holds the most spaces it may, and the page's link returns it to the command.",
"remedy": "Nothing on the caller's side corrects this at this version: no act deletes a space of the account's own, and the ceiling is the platform's. On Turn Zero Blueprint's sign-in, run the command again and choose one of the account's spaces on the confirm page."
},
{
"name": "space_not_owned",
"surfaces": [
"management_action",
"builder_sign_in"
],
"status": 403,
"owner": "MAPI-14",
"summary": "The request named a space the account does not hold, or cannot use as named, and nothing was recorded or created. For mint_token it is a space the issues grant would name that the account does not hold, or one space of an application's per-environment pair, whose tokens the platform keeps per environment and not in its vault. For relay_issue_act it is a space the account does not hold, whatever the credential, or one other than its token's grant names. For create_issue_space it is an identifier another owner's space stands under. For submit_manifest it is an issue_tracking entry naming an application's own space, this application's or another's, which binds by its own manifest alone, or a space the account does not hold. The platform's own space is held by the one account the platform names its owner. On Turn Zero Blueprint's confirm page and at its code exchange it is a space the request named or the confirmation chose that the account does not hold, or no longer holds at the exchange, nothing minted.",
"remedy": "Name a space list_issue_spaces answers for the account, or an application's own space as submit_manifest's receipt names it, or create one with create_issue_space; to reach another space, mint a token for it from a signed-in session of the account that holds it. A space of an application's per-environment pair is read and worked through the feedback actions naming `space`. For a manifest, leave `space` out, and the application holds a space of its own, or name a space of the account's own. On Turn Zero Blueprint's sign-in, sign in with the account that holds the space, or run the command again and choose a space the account holds.",
"members": {
"space": {
"type": "string",
"description": "The space the request named."
}
}
},
{
"name": "standing_stale",
"surfaces": [
"router"
],
"status": 503,
"owner": "SVC-L0-07",
"summary": "The serving router answers this on every path of the application's hostname, the shell and the reserved prefix included. The operator has set the standing's maximum age (`ROUTER_STANDING_MAX_AGE_S`, unbounded by default), and the control plane has not answered that router replica for longer than it, so the router cannot say whether the owning account still stands and serves nothing it holds. With no bound set the router serves what it holds through any outage and never answers this, and a recorded suspension or halt keeps its own refusal.",
"remedy": "Nothing on the caller's side corrects this. The refusal ends when the control plane answers the router again; the platform operator restores the control plane, and the platform status names the outage. An end user retries once the application answers again."
},
{
"name": "status_setting_unknown",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-76",
"summary": "set_status_setting named a setting the status record does not serve; the fourteen are probe_hostname, probe_path, samples_to_open, samples_to_close, probe_timeout_ms, stale_minutes, certificate_floor_days, error_counter_per_day, schedule_platform_outcomes_per_hour, mark_redeploy_concurrency, console_live_tail, unlimited_allowance_daily_signal_units, deploy_code_seconds, and token_code_seconds, and nothing is written.",
"remedy": "Repeat the request with one of the names the summary lists; a value outside a setting's bound is refused invalid_request with the bound in the detail."
},
{
"name": "storage_error",
"surfaces": [
"storage"
],
"status": 500,
"owner": "PLD-L0-80",
"summary": "An unexpected error while serving a storage route; the failure is recorded on the platform side under a reference the detail carries, and the detail never carries the error's own message.",
"remedy": "Retry the request. If the refusal repeats, report it and quote the reference its detail carries."
},
{
"name": "store_unavailable",
"surfaces": [
"management_action",
"realm_surface",
"builder_sign_in",
"storage",
"egress",
"logging",
"push",
"deploy_progress",
"workflow_start"
],
"status": 503,
"owner": "PLD-L0-67",
"summary": "The plane's database did not answer the credential lookup the guard runs, or on the storage, egress, and logging wires the gateway held no entry within its stale ceiling, so the request was not processed; retry it. On submit_manifest, the control store failed while the manifest's upstreams were written after its record; a write the failure followed is taken back where it can be, the manifest stays recorded, and the detail names the upstreams declared, those not, and any left standing. A failure while the realm member or the push entry's providers are recorded, after the upstreams, takes nothing back: what was recorded stands, and the detail names the realms, or the push configurations, done and those not. On the start-line route, the line was not stored; the workflow posts it again.",
"remedy": "Repeat the same request unchanged, since it was not processed and a repeat causes no duplicate effect. If the refusal continues, wait a short time and repeat the request again. On submit_manifest, the request was processed in part, and submitting the same manifest again before the next deploy or promote completes the declarations. Submitting it again also completes the realms and the push configurations."
},
{
"name": "subject_is_caller",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "API-L0-12",
"summary": "suspend_account named the calling credential's own account. A suspension ends every credential of the account it names and stops its serving, so an operator suspending its own account would end the session its reinstatement is called under. The standing is not written and the serving walk does not run.",
"remedy": "Name the account you mean to suspend. To stop your own account's service, ask another operator account to suspend it."
},
{
"name": "subject_missing",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account id_token carried no subject.",
"remedy": "Nothing in the realm's settings corrects this. Ask the client's tenant administrator to check the app registration that issues the token, then ask the end user to sign in again."
},
{
"name": "synthetic_account_fixed",
"surfaces": [
"management_action",
"builder_sign_in"
],
"status": 403,
"owner": "ACB-L0-79",
"summary": "An identity or a passkey joining a synthetic account, refused because a synthetic account holds exactly the identities its seed bound and signs in through the emailed-code route alone. The refusing sites are link_identity, the link ticket, the add-a-route start and its callback, the same-address interrupt ahead of its choice and its code and link exits, and the passkey registration routes.",
"remedy": "Nothing corrects this: a synthetic account gains no identity and no passkey. Sign in on the emailed-code route with the fixture address the seed bound, its code read through read_synthetic_signin_code."
},
{
"name": "synthetic_ceiling_reached",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAPI-16",
"summary": "A count the synthetic-account mode, or the synthetic_seed_purge grant, bounds is reached. The standing synthetic accounts at a seed; the standing synthetic applications, or those on a paid plan, at create_application or set_plan for a synthetic-owned application; or the accounts this operator's account seeded in the current UTC day. Under the synthetic_seed_purge grant, a seed also meets that grant's own ceiling: twelve standing synthetic accounts that the calling credential seeded. An account seeded under that grant holds no application on a paid plan: create_application and set_plan refuse one under the ceiling paid_applications_per_account, whose value is 0. The refusal names the ceiling and its value.",
"remedy": "Purge the synthetic accounts you no longer need, or wait for the lifetime sweep or the next UTC day; a ceiling is a constant of the mode or of the grant, and no call raises it. For paid_applications_per_account, create the application on the free plan, or leave it there.",
"members": {
"ceiling": {
"type": "string",
"description": "The name of the ceiling reached: standing_accounts, seeded_per_day, standing_applications, paid_applications, or, under the synthetic_seed_purge grant, standing_accounts_per_credential. For an account seeded under that grant, paid_applications_per_account names the ceiling on its paid-plan applications."
},
"value": {
"type": "integer",
"description": "The ceiling's constant, under the mode read or, for standing_accounts_per_credential and paid_applications_per_account, under the synthetic_seed_purge grant."
},
"standing": {
"type": "integer",
"description": "The count measured against the ceiling before the call. For seeded_per_day it is the accounts this operator's account seeded in the current UTC day. For standing_accounts_per_credential it is the standing synthetic accounts the calling credential seeded. For paid_applications_per_account it is the paid-plan applications the account holds, the one being moved counted out."
}
}
},
{
"name": "synthetic_estate_bounded",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An action outside the bound, reached by a minted token holding the synthetic_estate grant and no super_admin. The grant bounds its token to the rows it marks and to the rows whose admits mark names it, list_tokens and submit_feedback the two such rows. The rows marked access: anonymous lie outside the bound and answer the token as they answer every connection.",
"remedy": "Call the action from the owner's signed-in session, or under a token minted through mint_token without the synthetic_estate grant. The admitted member names the actions the bounded token reaches.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant that bounds the credential presented."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The actions the bound admits, in the enumeration's order: the rows the grant marks and the rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and are not listed."
}
}
},
{
"name": "synthetic_estate_disabled",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "A wire write of the synthetic estate — seed_synthetic_accounts or purge_synthetic_accounts — reached while the control plane's SYNTHETIC_ESTATE mode reads off, refused ahead of every other check. While the mode is off the two rows are unlisted as tools; the reads — read_synthetic_purge, read_synthetic_signin_code, and the reads of existing synthetic accounts — stand, and the platform's own lifetime sweep purges expired batches regardless. A stranded estate is purged after the mode is set.",
"remedy": "Nothing you call sets the mode, so ask the platform's operator to set it to compat or stress, then repeat the request. Meanwhile read_synthetic_purge, read_synthetic_signin_code, and the reads of existing synthetic accounts still work."
},
{
"name": "synthetic_posture_refuses",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An act the standing synthetic-account mode, or the caller's bounding grant, does not admit. A seed whose count is past the mode's per-call bound, a seed whose token_expires_in_days is past the mode's expiry bound, or all: true on the purge outside the stress mode or from a credential a synthetic grant bounds. Under the synthetic_seed_purge grant, a seed of more than one account, a seed whose token lives past one day, or a seed that names products. The refusal names the bound.",
"remedy": "Repeat within the mode's bounds — a smaller count, a shorter token_expires_in_days, explicit accounts in place of all — or ask the platform's operator to set the stress mode. Under the synthetic_seed_purge grant, seed one account for one day and leave products out: no mode widens that grant's bounds.",
"members": {
"bound": {
"type": "string",
"description": "The name of the bound that refused: accounts_per_seed, token_expiry_days, or products on a seed, all on a purge."
},
"value": {
"type": "integer",
"description": "The bound's constant, under the effective mode or under the caller's bounding grant, present on a seed's refusal that names accounts_per_seed or token_expiry_days."
},
"posture": {
"type": "string",
"description": "The mode the refused act met: the effective seed mode on a seed, the standing mode on a purge."
},
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The bounding grant the caller's credential holds without super_admin, present only where the grant is why the act was refused: all on a purge, or a seed past the grant's own bounds."
}
}
},
{
"name": "synthetic_seed_purge_bounded",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-16",
"summary": "An action outside the bound, reached by a minted token holding the synthetic_seed_purge grant and no super_admin. The grant bounds its token to seed_synthetic_accounts, purge_synthetic_accounts, and read_synthetic_purge, the three rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and answer the token as they answer every connection. A row another grant marks answers grant_required first.",
"remedy": "Call the action from the owner's signed-in session, or under a token minted through mint_token without the synthetic_seed_purge grant. The admitted member names the actions the bounded token reaches.",
"members": {
"grant": {
"type": "string",
"pattern": "^[a-z][a-z0-9_]*$",
"description": "The grant that bounds the credential presented."
},
"admitted": {
"type": "array",
"items": {
"type": "string"
},
"description": "The actions the bound admits, in the enumeration's order: the rows the grant marks and the rows whose admits mark names it. The rows marked access: anonymous lie outside the bound and are not listed."
}
}
},
{
"name": "target_environment_halted",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-41",
"summary": "promote, run_schedule, deploy: the environment the act targets is halted. `resume_environment` ends the halt, and the act is admitted after it. A deploy to a halted production is refused, and a deploy to a halted development environment is not, because it ends the halt itself (PLD-L0-41).",
"remedy": "Call resume_environment for the application and environment, then repeat the promote, run_schedule, or deploy. A deploy to a halted development environment needs no resume, because the deploy itself ends the halt."
},
{
"name": "tenant_mismatch",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The work-account id_token names an Entra tenant other than the configured one.",
"remedy": "Ask the end user to sign in with an account that belongs to the configured tenant. If the wrong tenant is configured, correct entra.tenant with configure_realm, then ask the user to sign in again."
},
{
"name": "token_code_refused",
"surfaces": [
"management_action"
],
"status": 403,
"owner": "MAPI-23",
"summary": "mint_token's exchange on the HTTP action route under a token code, the one-time code a mint naming `code_challenge` puts in its line, is refused. The code is unknown, expired, or already presented, by an earlier run of the line or by another party; its verifier does not match; the body names more than `code_verifier`; the account is suspended; or the session that minted it has ended. One refusal, alike in name, status, and detail, answers every such state, so it says nothing of whether a code existed. Every presentation there that the platform finds spends the code. Answered only where the token code form is served.",
"remedy": "Call `mint_token` again with the challenge the turnzero-cloud command printed, and run the line it answers once, as given."
},
{
"name": "token_exchange_failed",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-09",
"summary": "The provider token endpoint refused the exchange, answered no id_token, or answered nothing within the platform's round-trip bound, on the work-account or the Apple route.",
"remedy": "On the work-account route, store the app registration's current client secret value again with store_secret, naming this application and the realm's environment, under the configured name, and correct entra.client_id with configure_realm where read_realm shows it differs from the registration's client id. On the Apple route, store the signing key again under apple.key_secret_name and check the Services ID, team, and key identifiers. Then ask the end user to sign in again; where the refusal repeats at once, the provider is not answering, and it passes."
},
{
"name": "token_scope_refused",
"surfaces": [
"management_action",
"realm_surface"
],
"status": 403,
"owner": "API-L0-17",
"summary": "An application-bounded minted token named a subject of another application. The same name answers such a token on the application-less builder-realm form of issue_invitation, revoke_invitation, list_invitations, or configure_realm (MAPI-09), on every form of the four feedback actions, which name no application, and on undeclare_storage_area for an area outside its reach (OST-L0-03). On undeclare_upstream, it answers every application-bounded token, since the account's own credential alone ends an upstream (API-L0-17).",
"remedy": "Address the request to the token's own application, or use a credential that reaches the named one: an account-wide session, or a token bounded to that application or to the account. A wider reach is a second token, minted from a signed-in session through mint_token, never an edit to the held one.",
"members": {
"scope": {
"type": "object",
"description": "The bound of the token presented: the one application it reaches, outside which the request's subject lies.",
"properties": {
"kind": {
"type": "string",
"description": "The kind of bound, always application here."
},
"application": {
"type": [
"string",
"null"
],
"description": "The id of the application the token is bounded to, null where the credential's bound names none."
}
}
}
}
},
{
"name": "transfer_grant_expired",
"surfaces": [
"management_action",
"storage"
],
"status": 403,
"owner": "OST-L0-08",
"summary": "The transfer grant passed its expiry; its minter mints another. A deploy upload's grant admits its start before its expiry alone.",
"remedy": "Mint a new grant for the same area, file, and direction: the application backend on the mint route, or mint_upload_grant for an upload. For an export's download, call mint_download_grant again and run the line it answers, which skips the files already on disk. Repeat the file act under the new grant before its expiry. For a deploy upload, call `deploy` with the application, naming no environment and none of `zip_sha256`, `artifact`, and `upload`, and run the line it answers at once: mint_upload_grant and the mint route refuse the deploy area. Where the refusal's detail names a start-only retry, or read_status names this upload as the `pending_upload` of the environment the deploy goes to, with a `retry`, make that call from your tool instead."
},
{
"name": "transfer_grant_not_admitted",
"surfaces": [
"management_action",
"mcp_server",
"storage",
"egress",
"realm_surface",
"push",
"deploy_progress"
],
"status": null,
"owner": "OST-L0-08",
"summary": "The transfer grant object storage mints serves its one file act and is refused by name everywhere else (403; a 401 challenge at the MCP server). An export's download grant serves `GET` of a named file alone: its export's own files, and its application's stored files created by the time its export listed them. A stored file created later answers `no_such_file` under it, as an absent name does, and not this refusal. A deploy upload's grant also serves its upload's one start on `deploy`, naming its own application, the environment its preparing call recorded, and upload. After that start, it serves the deploy command's progress reads of its own deploy inside their window, and the progress read refuses by this name every other credential and that grant before its start.",
"remedy": "Present the grant only on the one file route it names, PUT or GET /storage/v0/areas/{area}/files/{name}, in the direction it was minted for. Under an export's download grant, read a file by its name, never a listing, the deploy area, or another application's area. Where a stored file the export's manifest names is refused by this name, call `mint_download_grant` again and run the line it answers. For any other act, present the credential that surface admits, for example a signed-in session or a minted token on the management surface. A deploy upload's grant starts only its own upload and then reads only that deploy's progress, as the turnzero-cloud command does under the grant its preparing `deploy` call answers. To read a deploy under your own credential, call `read_status`.",
"members": {
"credential_kind": {
"type": "string",
"description": "The kind of the credential refused: transfer_grant on the storage surface, the actions, and every other surface, and on the deploy command's progress read any kind presented."
}
}
},
{
"name": "transfer_grant_spent",
"surfaces": [
"management_action",
"storage"
],
"status": 403,
"owner": "OST-L0-08",
"summary": "The upload grant was spent by a write that landed; an upload grant serves one write. A deploy upload's grant is also spent by a later preparing call of `deploy` for the application, which replaces the upload, and by a later line-form call that ends it unstarted. Its one start on `deploy` spends it too, a start the platform refused included. A deploy upload's grant answers its zip sent again after its write landed with 200, writing nothing, until it expires and unless a later deploy call replaced the upload, and refuses other bytes.",
"remedy": "Under any grant but a deploy upload's, do not resend the write that spent it. For a further write to the file, mint a new upload grant, on the mint route or through mint_upload_grant, then send that write under it. For a deploy upload a later `deploy` call replaced or ended, call deploy with the application, naming no environment and none of `zip_sha256`, `artifact`, and `upload`. Run the command it answers once, as given, from the application's folder, or `command_windows` on Windows; it deploys and prints its progress, then read read_status. Where these bytes were not written and, once the first run has ended, read_status shows neither this upload pending nor its deploy, the first write never landed. For a new deploy, make the same call and run its line: mint_upload_grant and the mint route refuse the deploy area. Where read_status names this upload as the `pending_upload` of the environment the deploy goes to, with a `retry`, make that call from your tool to start it."
},
{
"name": "undeclared_area",
"surfaces": [
"management_action",
"storage"
],
"status": 404,
"owner": "OST-L0-01",
"summary": "No area by that name is declared for the account, on a file route, the grant mint route, or mint_upload_grant. Mint it with PUT /storage/v0/areas/{area} or declare_storage_area.",
"remedy": "Declare the area first with declare_storage_area or PUT /storage/v0/areas/{area}, then repeat the file request or the mint. Check the name against list_storage_areas, which lists the areas the account has declared."
},
{
"name": "undeclared_upstream",
"surfaces": [
"egress"
],
"status": 404,
"owner": "EGW-L0-01",
"summary": "No upstream by that name is declared for the account; declare_upstream declares it.",
"remedy": "Check the name against list_upstreams, and declare the upstream with declare_upstream where it is missing. Then send the call again."
},
{
"name": "unknown_action",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "MAPI-10",
"summary": "No action by that name in the contract version.",
"remedy": "Check the action name against the Management actions reference page, then repeat the request with a listed name. The documentation's page manifest, docs.json, records the contract version its pages describe."
},
{
"name": "unknown_application",
"surfaces": [
"router"
],
"status": 404,
"owner": "SVC-L0-07",
"summary": "No live application carries the label, or its owner row is absent.",
"remedy": "Send the request to the application's current hostname, which list_applications answers to its developer, and allow the router's bounded interval after a rename. A deleted application's hostname never answers again, and where the owning account is being deleted nothing on the caller's side corrects this."
},
{
"name": "unknown_environment",
"surfaces": [
"management_action"
],
"status": 400,
"owner": "PLD-L0-40",
"summary": "deploy on the HTTP API: the named environment is neither development nor production, the platform’s two. Over MCP, the argument’s own validation refuses such a value before the call.",
"remedy": "Name `development` or `production`, or name none: the deploy then goes to production on an application with one environment and to development on one with two. With two, a version reaches production through promote."
},
{
"name": "unknown_host",
"surfaces": [
"router"
],
"status": 404,
"owner": "SVC-L0-07",
"summary": "The Host line is not under the serving suffix, or, on the serving router's invoke endpoint, it is a label under the suffix — that endpoint answers on the router's own hostname alone.",
"remedy": "Send the request to one of the application's two managed hostnames, the production hostname or the development hostname whose first label ends in -dev, as list_applications answers them. On the invoke endpoint nothing on the caller's side corrects this, because the platform's scheduled runs alone use that path."
},
{
"name": "unknown_route",
"surfaces": [
"storage"
],
"status": 404,
"owner": "OST-L0-02",
"summary": "The path is none of the storage routes.",
"remedy": "Send the request to one of the storage routes. One file is at /storage/v0/areas/{area}/files/{name}, a listing at /storage/v0/areas/{area}/files, an area declaration at PUT /storage/v0/areas/{area}, and a transfer grant at POST /storage/v0/grants."
},
{
"name": "unknown_upstream",
"surfaces": [
"egress"
],
"status": 404,
"owner": "EGW-L0-01",
"summary": "The path names no upstream segment, or its upstream segment holds a NUL character (U+0000).",
"remedy": "Send the call to /egress/v0/<upstream>/<path>, the declared upstream's name standing where <upstream> is."
},
{
"name": "unrecognized_invitation",
"surfaces": [
"realm_surface",
"builder_sign_in"
],
"status": 403,
"owner": "ACS-L0-08",
"summary": "An invitation-only realm: creation without an invitation, or with one naming another address, or with a spent, expired, or revoked one — the one name for every case, on an end-user realm's surface and on the builder realm's sign-in page (ACB-L0-77).",
"remedy": "Sign in through the URL of a standing invitation, using the address it names, or ask the realm's author (the platform operator for the builder realm) for a fresh one. The author reads an invitation's state through list_invitations and mints a new one through issue_invitation."
},
{
"name": "upload_hash_mismatch",
"surfaces": [
"management_action",
"storage"
],
"status": 409,
"owner": "OST-L0-08",
"summary": "The bytes a write under a deploy upload's grant carries, or the stored file that upload's start reads, are not the zip whose SHA-256 the turnzero-cloud command's preparing `deploy` call named as `zip_sha256`. A refused write writes nothing and leaves the grant unspent, and a refused start deploys nothing.",
"remedy": "Call `deploy` with the application, naming no environment and none of `zip_sha256`, `artifact`, and `upload`, and run the command it answers once, as given, from the application's folder, or `command_windows` on Windows; it deploys and prints its progress, then read `read_status`.",
"members": {
"received_sha256": {
"type": "string",
"description": "The SHA-256 of the bytes refused, 64 lower-case hexadecimal characters: the body the write carried, or the stored file the start read."
},
"expected_sha256": {
"type": "string",
"description": "The SHA-256 the preparing `deploy` call named as `zip_sha256`, 64 lower-case hexadecimal characters, which the upload's grant records."
},
"credential_kind": {
"type": "string",
"description": "The kind of the credential whose binding refused the bytes, transfer_grant: the upload's grant, at the write and at the start alike."
}
}
},
{
"name": "upload_not_found",
"surfaces": [
"management_action"
],
"status": 404,
"owner": "PLD-L0-86",
"summary": "deploy: the upload the call names holds no file its own grant wrote. It was not uploaded yet, its grant expired unused, a later preparing call replaced it, a later line-form call ended it, or a deploy that has ended already read it. The command's start under the upload's grant also answers it before the grant's write lands.",
"remedy": "Call `deploy` with the application, naming no environment and none of `zip_sha256`, `artifact`, and `upload`, run the line it answers once, as given, from the application's folder, and make the answer's `next` call. Where the detail says a deploy already read the upload, read that deploy's outcome with list_versions instead: a new deploy would deploy it again."
},
{
"name": "upstream_ended",
"surfaces": [
"router"
],
"status": 502,
"owner": "HST-L0-03",
"summary": "The application's process ended while the request was in flight, and the intermediary in front of the process answered for it before any response header reached the client: the cluster's interceptor's 502 on the pod grain, the cell ingress's 503 on the container grain. The serving router names the ending only where the leg's answer is that grain's fixed shape whole, and answers 502 with the elapsed duration; an answer of any other shape, an application's own 502 or 503 among them, passes through untouched. The router's record names the application, the host, the path, the grain, the intermediary's status, and the duration, and on a scheduled run the schedule and the run; the invoke envelope carries the ending as upstream_failed with upstream_ended named in its detail.",
"remedy": "Retry the request: the process restarts under the platform's supervision and a retry reaches the restarted process. Read the router's upstream_ended record through read_logs with source router, and, where the harness ended the process, the container source's process_ended line naming the handler that did not yield."
},
{
"name": "upstream_failed",
"surfaces": [
"router"
],
"status": 502,
"owner": null,
"summary": "The router proxy to the application failed before any status reached the wire.",
"remedy": "Retry the request. If the refusal repeats, report it with its detail, which names the failure's code and never an address inside the platform's network."
},
{
"name": "upstream_key_is_bound",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "MAN-14",
"summary": "declare_upstream: a setting binds the credential name, in the bound application's recorded manifest, in either environment's serving row, or in a deploy, promote, or restart in flight to either. Its value is then injected into the container, and a key the gateway applies at its edge never is (EGW-L0-03). The detail names the setting and where it is bound. Refused before the write, nothing was written; refused after it, the write is taken back, or stands as written where the detail says so. On submit_manifest, a binding recorded after the submission's check feeds an entry's credential once the entry is written; that write is taken back where it can be, the manifest stays recorded, and the detail names the upstreams declared, those not, and any left standing.",
"remedy": "Store the upstream's key under another name and declare the upstream naming it. Or remove the binding from the manifest's settings, call submit_manifest, deploy or promote each environment whose running copy carries it once any act in flight that carries it has ended, and declare the upstream again. Carry the upstream's `settings` in that call, or omit the member, which keeps them; `settings` null removes them and ends the upstream's egress keys. Where the detail says the declaration stands, declare it again with another credential name, or remove the binding. On submit_manifest, change the entry's credential_name or remove the binding, then submit the manifest again before the next deploy or promote."
},
{
"name": "upstream_scope_refused",
"surfaces": [
"egress"
],
"status": 403,
"owner": "EGW-L0-08",
"summary": "The credential does not reach the upstream declaration. An upstream admits its own application and an account-wide credential that no bounding grant bounds. A minted token the synthetic_seed_purge, synthetic_estate, publication, feedback_queue, or issues grant bounds reaches no upstream of the account (MAPI-16).",
"remedy": "Repeat the call with a credential the upstream admits: an account-wide credential that no bounding grant bounds, or the credential of the application the upstream is bound to. A wider reach is a second token, minted from a signed-in session through mint_token, never an edit to the held one. For a token the synthetic_seed_purge, synthetic_estate, publication, feedback_queue, or issues grant bounds, mint a token without the grant, or call from the owner's session."
},
{
"name": "upstream_timeout",
"surfaces": [
"egress"
],
"status": 504,
"owner": "EGW-L0-05",
"summary": "The upstream exceeded the time bound; a stream is ended with this terminal event.",
"remedy": "Retry the request. If the refusal repeats, report it with its detail."
},
{
"name": "upstream_unreachable",
"surfaces": [
"egress"
],
"status": 502,
"owner": "EGW-L0-05",
"summary": "The upstream connection failed or a mid-stream transport failure; or the `issue-tracking` upstream's 2xx answer at the `report` level could not be read as the wire's JSON object (EGW-L0-03).",
"remedy": "Retry the request. If the refusal repeats, report it with its detail."
},
{
"name": "usage_over_quota",
"surfaces": [
"router",
"storage",
"push"
],
"status": 429,
"owner": "ACB-L0-26",
"summary": "The application stands over its plan's quantity for a measure in the current UTC month (ACB-L0-26). The serving router answers this on every application leg of either hostname while backend actions or data transfer is over. The served shell asset and the realm leg alone are excepted. In the router's answer, `Retry-After` carries the seconds to the first instant of the next month, and the detail names that instant. The invoke route answers it in its refused envelope, and the schedule service records the run skipped (SCH-L0-04). The object storage surface answers it on a file put to an area bound to an application whose stored-data state is over (OST-L0-05). Gets, lists, and deletes continue. The state clears at the month roll, a plan change, or a quota change. On the push surface, the send would take the month's accepted deliveries past the plan's push-messages-capacity cell, and nothing was accepted.",
"remedy": "For backend actions or data transfer, wait until the next month's first instant, which the detail names, or move the application to a larger plan with set_plan. For stored data, move to a larger plan with set_plan, or reduce the stored files and database data and wait for the next daily check to read the figure within. On the push surface, wait for the month's first instant in UTC, or move to a larger plan."
},
{
"name": "user_suspended",
"surfaces": [
"realm_surface"
],
"status": 403,
"owner": "ACS-L0-08",
"summary": "The end user is suspended in this realm until reinstatement.",
"remedy": "Nothing the end user does lifts the suspension. The application's author restores the user's standing through reinstate_end_user, after which the user signs in again."
},
{
"name": "version_already_serving",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-43",
"summary": "roll_back: the version named is already production's serving version. A re-mint of the production platform credential is a production deploy's or `promote`'s act, not `roll_back`'s.",
"remedy": "Call roll_back naming a different deployed version. To re-mint production's platform credential, call promote with that version on an application with two environments; on one, deploy again, which re-mints it for the new version."
},
{
"name": "version_image_pruned",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "PLD-L0-63",
"summary": "promote, roll_back: the version named is a deployed row whose image the platform's retention deleted from the cell registry. The cell registry keeps the images of the serving version and the twenty most recent deployed versions per environment. A promote reuses the deploy's image, so the version cannot be promoted. `list_versions` answers `promotable` per row. A new deploy builds a new version.",
"remedy": "Choose a version that list_versions marks promotable, or deploy the artifact again as a new version and, on an application with two environments, promote that."
},
{
"name": "version_keeping_unsupported",
"surfaces": [
"management_action",
"storage"
],
"status": 400,
"owner": "OST-L0-01",
"summary": "version_keeping true refuses at v0: the surface retains no prior versions.",
"remedy": "Send the declaration again with version keeping declared false (version_keeping: false in declare_storage_area). No setting on the caller's side turns version keeping on at this version."
},
{
"name": "version_mismatch",
"surfaces": [
"storage"
],
"status": 412,
"owner": "OST-L0-07",
"summary": "The conditional put names a version no longer current; current_version rides beside.",
"remedy": "Read current_version from the refusal body. If the write still applies over the stored content, send the put again with If-Match set to that version."
},
{
"name": "version_reused",
"surfaces": [
"management_action"
],
"status": 409,
"owner": "LC-04",
"summary": "publish_library begin: an entry of the catalog keeps a version the served catalog already holds under a different closure hash. A version names one set of bytes, so the begin writes nothing. The refusal names the entry, the version, and both closure hashes, each where it holds its shape.",
"remedy": "Bump the entry's version and run the publish again from `begin`, or restore the entry's bytes to the served closure. Do not retry the same version with different bytes.",
"members": {
"entry": {
"type": "string",
"description": "The name of the entry whose version is reused, left out where it is not in a library entry name's shape."
},
"version": {
"type": "string",
"description": "The version the entry keeps, which the served catalog already holds under another closure, left out where it is not in a version's shape."
},
"served_closure_hash": {
"type": "string",
"description": "The closure hash the served catalog records for the entry, left out where it is not 64 lower-case hexadecimal characters."
},
"incoming_closure_hash": {
"type": "string",
"description": "The closure hash this catalog states for the entry, left out where it is not 64 lower-case hexadecimal characters."
}
}
},
{
"name": "window_ended",
"surfaces": [
"router",
"harness"
],
"status": 504,
"owner": "HST-L0-03",
"summary": "The request ran past the bounded execution window (HST-L0-02, the platform's configuration keyed by invocation kind). Where no response header has reached the client, the serving router answers 504 with the elapsed duration. Where the response is streaming, the router cuts the application leg. The router's record names the application, the host, the path, and the duration. On a scheduled run the router's record names the schedule kind, the schedule, and the run. The harness's own line in the container's log says whether the handler yielded on its signal. Where the handler did not yield within the grace, `process_ended` names the requests the process end cut beside it. The harness records this refusal and never answers it.",
"remedy": "Read the router's window_ended record through read_logs with source router for the path and the duration, and the container source for whether the handler yielded on its signal. Make that handler finish inside the window, ending its response when request.signal aborts."
},
{
"name": "workflow_keys_unavailable",
"surfaces": [
"workflow_start"
],
"status": 503,
"owner": "PLD-L0-76",
"summary": "The start-line route could not verify the run's token against GitHub's published key set, which did not answer or held no key of the token's key id yet, so the line was not stored.",
"remedy": "Post the line again; the start-line script retries once on its own."
},
{
"name": "workflow_not_admitted",
"surfaces": [
"workflow_start"
],
"status": 403,
"owner": "PLD-L0-76",
"summary": "The run's token verified but names what the start-line route does not admit: another repository or owner than the plane's setting names, a ref other than the trunk's, an unlisted workflow file, or a reusable workflow's reference. The detail names the check.",
"remedy": "Nothing on the caller's side corrects this for that run. Only a scheduled workflow of the named repository, run on its trunk, records a start."
},
{
"name": "workflow_token_invalid",
"surfaces": [
"workflow_start"
],
"status": 401,
"owner": "PLD-L0-76",
"summary": "The run's token did not verify: its signature, its algorithm (RS256 alone), its issuer, its audience, or its instants, read under the route's clock tolerance. The detail names the check.",
"remedy": "Request a fresh token for the start-line route's audience in the same run and post it again."
}
]
}