Every API here is available over the APIs.io API and to AI agents over MCP.
openapi: 3.2.0
info:
title: Agentic Atlas Nodes API
description: 'Read-only JSON access to the Agentic Atlas: field-tested patterns for
designing agentic systems — skills, subagents, plugins, and multi-agent
workflows. **No authentication.** Every operation is public and unauthenticated. There
is no key to obtain, no quota to register for, and no account. **Read-only.** Human operations use `GET`; `/api/agent/*` uses `POST` with
JSON arguments to read the same Agent projection as MCP and the public CLI. Nothing here creates, updates, or deletes. Three
consequences worth stating, because they are what a general-purpose client
goes looking for and will not otherwise find:
* No `Idempotency-Key`. A safe `GET` has nothing to replay-protect, so the
header is neither required nor honoured. Retry a failed call directly. * No asynchronous jobs. Every operation answers in one round trip. There is
no job to submit, no status to poll, and no callback to register. * No sandbox. Every operation reads published data with no key, no quota,
and no side effect, so the live surface *is* the safe one to develop
against — a second environment would only serve a second Release. The machine-readable form of all three is `info.x-api-shape`. **One Release at a time.** The Atlas publishes one sealed Release. Every
reading of it carries an `X-Catalog-Revision` header naming it, and a
refusal carries none, so take the revision off an answer and never off a
refusal. Which is which is a property of the response, not of the status: a
response declared with a reading''s schema is a reading whatever its status,
and a response declared as `AtlasError` is a refusal. Today every `200` is a
reading, and so are two `404`s, `readDecision`''s not-found miss and
`readTour`''s unsealed walk, each declared with its own reading''s schema and
this header; every response declared as `AtlasError` carries no revision. Two responses with the same value are guaranteed to describe the same
Atlas. A promotion replaces the active Release wholesale rather than editing
one in place, so a long-running client that sees the header change has
crossed a promotion and should re-read rather than merge. **Versioning.** Addresses are stable and are not prefixed with `/v1/`; the
protocol version travels in a header instead, so an additive change never
moves a URL. Every API response carries `API-Version: 2`, declared on every
response in this document with its one permitted value, and restated in
`info.x-api-version`. The same header may be sent *on* a request to pin the
version a client was written against: pin the version you parse, and a
deployment serving a different one refuses with `400` instead of handing you
a payload you will misread. Omitting it means "whatever is current", so no
existing client has to change. This protocol version is independent of the
content Release named by `X-Catalog-Revision`. Additive changes — a new
operation, a new optional parameter, a new field in a response — stay within
version 1, so parse leniently. A breaking change increments `API-Version` and is
announced first under the policy below. **Deprecation.** A deprecated operation returns `Deprecation: true` and an
HTTP-date `Sunset` header for at least 180 days before removal, and is
marked `deprecated: true` in this document for that whole interval. Both
headers are declared on every operation here so a client can read the
retirement signal without being told where to look; both are absent while an
operation is current. `info.x-deprecation-policy` carries the notice window,
the two header names with their RFCs, and `deprecatedOperations` — the
authoritative list, which is empty. No operation is deprecated today. **Human API pagination.** There is none, and that is the contract rather than a gap. Reads are *bounded*, not paged: an operation that could return many rows
takes a `limit` whose default and maximum are declared on the parameter
itself.'
version: v1.1.0
contact:
name: Agentic Atlas
url: https://agentic-atlas.dev/contact
email: hello@agentic-atlas.dev
license:
name: Source-available; reading and use permitted, republication not
url: https://agentic-atlas.dev/why
x-api-version: '2'
x-version-header: API-Version
x-deprecation-policy:
minimumNoticeDays: 180
deprecationHeader: Deprecation
deprecationHeaderSpecification: RFC 9745
sunsetHeader: Sunset
sunsetHeaderSpecification: RFC 8594
deprecatedOperations: []
versioningScheme: header
versionHeader: API-Version
currentVersion: '2'
versionPinning: Optional and bidirectional. A request may state API-Version to pin the version it was written against; a value other than the current one is refused 400 rather than answered. Omitting it accepts whatever version is current.
breakingChangePolicy: A breaking change increments the API-Version header. Additive changes — a new operation, a new optional parameter, a new response field — retain it, so a client must parse leniently.
x-api-shape:
readOnly: true
methods:
- GET
- POST
writeOperations: []
authentication: none
idempotencyKeys: Not applicable. Every operation only reads published data, so there is nothing to replay-protect; `Idempotency-Key` is neither required nor honoured. Retry a failed call directly.
asynchronousOperations: None. Every operation answers in one round trip — no job to submit, no status to poll, no callback to register.
sandbox: None, and none is needed. Every operation is a public read of published data with no key, no quota, and no side effect, so the live surface is the safe one to develop against.
batchOperations:
readCards: ids
compare: ids
resolveName: name
batchStyle: 'Human batchOperations use repeated query parameters on GET; agentBatchOperations use an ids array in a JSON POST body. Each is atomic: the whole call is refused rather than partially answered, so no caller has to notice a gap in a payload that looks complete. The refusal names the id that spoiled the batch — drop it and re-batch the rest in one call. Falling back to one call per id spends a request per id to learn what the refusal already said.'
agentBatchOperations:
agent_cards: JSON body ids array; atomic
x-pagination:
appliesTo: Human GET operations; Agent POST operations declare x-pagination per operation
style: bounded-read
boundParameter: limit
offsetParameter: null
pageParameter: null
cursorParameter: null
nextLinkField: null
truncationFields:
- total
- returned
- truncated
truncationReportedBy:
- readLinks
- readTermUsages
description: Reads are bounded, not paged. `limit` caps one response; it does not select a window, and there is no offset, page number, or cursor to advance — no continuation state exists to carry. Ordering is the publisher's and is stable within one Release, so a bounded read is a prefix rather than a sample. Where a bound can cut, the payload reports it in-band; the remainder is reached by raising `limit` toward the maximum declared on the parameter, or by narrowing the subject. A client written for cursors should not be pointed here.
x-availability:
healthProbe: /healthz
readinessProbe: /readyz
statusDocumentation: /status
statusPage: null
incidentFeed: null
slaPublished: false
retryableStatuses:
- 503
description: 'Availability is best effort and no service level is promised. /healthz answers whenever the process is running and reads no database; /readyz answers 200 when this deployment can serve and 503 when it cannot, naming every check, the active Release and its Catalog revision. A 503 from an operation is the same condition and the same retry: the address is unchanged and the operation is not retired. There is no external status page, no incident feed and no uptime history — /status states each refusal this API can return with its recovery, and says that too.'
servers:
- url: https://agentic-atlas.dev
description: The origin this API is published at
tags:
- name: Nodes
paths:
/api/nodes/{canonical_id}:
get:
summary: Read one complete Node
operationId: readNode
parameters:
- name: API-Version
in: header
required: false
schema:
type: string
enum:
- '2'
description: The protocol version this client was written against. Omit it to be served whatever version is current; send it to be refused with 400 rather than answered in a version you cannot parse. The value to send is the one every response states in the header of this name.
- name: canonical_id
in: path
required: true
schema:
type: string
title: Canonical Id
description: The Node's canonical id. Canonical ids are not guessable — reach one through resolveName, orient, or search.
- name: section
in: query
required: false
schema:
anyOf:
- type: string
- type: 'null'
title: Section
description: Read one section by slug instead of the whole Node. An unknown slug is a 404, not an empty read.
responses:
'200':
description: The requested reading of the active Release.
content:
application/json:
schema: {}
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
RateLimit-Limit:
$ref: '#/components/headers/RateLimitLimit'
RateLimit-Remaining:
$ref: '#/components/headers/RateLimitRemaining'
RateLimit-Reset:
$ref: '#/components/headers/RateLimitReset'
RateLimit:
$ref: '#/components/headers/RateLimit'
RateLimit-Policy:
$ref: '#/components/headers/RateLimitPolicy'
X-Catalog-Revision:
$ref: '#/components/headers/CatalogRevision'
'400':
description: Nothing was read. The request pinned an API-Version this deployment does not serve, a Human query is invalid, or an Agent JSON body is malformed. AtlasError names its cause in `error.type`; AgentError uses `error.code`. For an unsupported version, resend with the version the response header states, or without the header. For an invalid query or JSON body, correct the input before retrying. The direct version refusal spends from the rate-limit window but carries none of its advisory headers; routed query and body refusals do, so this shared 400 response cannot require them.
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
content:
application/json:
schema:
$ref: '#/components/schemas/AtlasError'
'404':
description: 'No such subject in the active Release. The address is an operation and the request parsed; it is the subject that is unknown. An operation that refuses its miss does so in `AtlasError`, and `error.type` names the class it was looked for as. An operation that answers its miss as a reading instead sends the same payload as its 200, declared on this status through the same schema, carrying X-Catalog-Revision and no `error` key: readDecision (`DecisionRead` with `outcome` `not-found` and `decision` null) and readTour (`LearningPathsRead` with `paths` empty). A 404 at an address that names no operation is a different refusal, `UnknownOperation`, and is declared on no operation here because none is published there.'
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
RateLimit-Limit:
$ref: '#/components/headers/RateLimitLimit'
RateLimit-Remaining:
$ref: '#/components/headers/RateLimitRemaining'
RateLimit-Reset:
$ref: '#/components/headers/RateLimitReset'
RateLimit:
$ref: '#/components/headers/RateLimit'
RateLimit-Policy:
$ref: '#/components/headers/RateLimitPolicy'
content:
application/json:
schema:
$ref: '#/components/schemas/AtlasError'
'405':
description: Nothing was read. The address names an operation; the method does not. Resend under one of the methods the `Allow` header names — and note that this API has no write operations at all, which info.x-api-shape states. Agent reads use POST; Human reads use GET and HEAD.
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
RateLimit-Limit:
$ref: '#/components/headers/RateLimitLimit'
RateLimit-Remaining:
$ref: '#/components/headers/RateLimitRemaining'
RateLimit-Reset:
$ref: '#/components/headers/RateLimitReset'
RateLimit:
$ref: '#/components/headers/RateLimit'
RateLimit-Policy:
$ref: '#/components/headers/RateLimitPolicy'
Allow:
$ref: '#/components/headers/Allow'
content:
application/json:
schema:
$ref: '#/components/schemas/AtlasError'
'429':
description: Nothing was read. More than the published number of requests came from this address inside one window, and the refusal was composed before the operation ran. Wait the seconds named in `Retry-After` and resend; the request itself is fine. Every response, this one included, states the window in `RateLimit-Limit`, `RateLimit-Remaining` and `RateLimit-Reset`, so a client can pace itself and never arrive here.
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
RateLimit-Limit:
$ref: '#/components/headers/RateLimitLimit'
RateLimit-Remaining:
$ref: '#/components/headers/RateLimitRemaining'
RateLimit-Reset:
$ref: '#/components/headers/RateLimitReset'
RateLimit:
$ref: '#/components/headers/RateLimit'
RateLimit-Policy:
$ref: '#/components/headers/RateLimitPolicy'
Retry-After:
$ref: '#/components/headers/RetryAfter'
content:
application/json:
schema:
$ref: '#/components/schemas/AtlasError'
'503':
description: The Catalog is unreachable, or no Release is active. The address is fine and the request parsed; retry it. Readiness is reported at /readyz, and /status states this and every other refusal with its recovery.
headers:
API-Version:
$ref: '#/components/headers/ApiVersion'
Deprecation:
$ref: '#/components/headers/Deprecation'
Sunset:
$ref: '#/components/headers/Sunset'
RateLimit-Limit:
$ref: '#/components/headers/RateLimitLimit'
RateLimit-Remaining:
$ref: '#/components/headers/RateLimitRemaining'
RateLimit-Reset:
$ref: '#/components/headers/RateLimitReset'
RateLimit:
$ref: '#/components/headers/RateLimit'
RateLimit-Policy:
$ref: '#/components/headers/RateLimitPolicy'
content:
application/json:
schema:
$ref: '#/components/schemas/AtlasError'
description: 'The whole Node at one canonical address: every section, in order, with its prose and its references. This is the most expensive payload on the surface — prefer a Card when the publisher''s claims are all you need.'
deprecated: false
tags:
- Nodes
components:
schemas:
AtlasError:
type: object
title: Atlas error
description: 'The Atlas''s own refusal: a nested `error` object naming what could not be answered. Show `error.message`; branch on the HTTP status, or on `error.type` for a finer split.'
properties:
error:
type: object
properties:
code:
type: integer
description: The HTTP status, repeated in the body. Omitted by readNode, so read the status rather than relying on this.
type:
type: string
description: 'The class of refusal — `NodeNotFound`, `InvalidBound`, `CatalogUnavailable`, and the like. The refusals composed before the operation runs name themselves here too: `UnsupportedApiVersion` on a 400, `RateLimited` on a 429, `MethodNotAllowed` on a 405, and `UnknownOperation` on a 404 at an address that names no operation at all.'
message:
type: string
description: One sentence naming what could not be answered.
required:
- type
- message
required:
- error
headers:
Sunset:
description: The HTTP-date after which this operation may be removed (RFC 8594). Accompanies Deprecation and is set at least 180 days ahead. Absent on a current operation, and absent everywhere today.
required: false
schema:
type: string
format: http-date
Deprecation:
description: Present, with the value `true`, only while this operation is inside its retirement notice window (RFC 9745). Absent on a current operation, and absent everywhere today — no operation is deprecated. See info.x-deprecation-policy.deprecatedOperations.
required: false
schema:
type: string
enum:
- 'true'
CatalogRevision:
description: The active Release's Catalog revision. Two responses carrying the same value describe the same Atlas; a changed value means a promotion happened between the calls.
required: true
schema:
type: string
RateLimit:
description: 'The current API window as one advisory field: `limit`, `remaining`, and seconds until `reset`. Present on every API response so a client can pace itself before a refusal. The direct unsupported-version 400 is the one exception.'
required: true
schema:
type: string
example: limit=300, remaining=299, reset=60
Allow:
description: 'The methods this address does answer. Present only on a 405, where it is the whole recovery in the way Retry-After is on a 429: resend the same request under one of these.'
required: true
schema:
type: string
RateLimitRemaining:
description: The requests left in the current API window after this one. Present on every API response except the direct unsupported-version 400.
required: true
schema:
type: integer
minimum: 0
maximum: 300
ApiVersion:
description: The stable API protocol version. Additive changes retain this value; a breaking change increments it. Independent of the content Release named by X-Catalog-Revision. Send this value back as a request header to pin it — see the parameter of the same name on any operation.
required: true
schema:
type: string
enum:
- '2'
RateLimitPolicy:
description: 'The policy that produced this window: the `api` policy name, its request quota (`q`), and its window in seconds (`w`). Present on every API response except the direct unsupported-version 400.'
required: true
schema:
type: string
enum:
- '"api";q=300;w=60'
RetryAfter:
description: 'How many seconds until the rate-limit window reopens. Present only on a 429, where it is the whole recovery: wait this long and resend the same request unchanged.'
required: true
schema:
type: integer
minimum: 1
maximum: 60
RateLimitLimit:
description: The maximum requests admitted in the current API window. Present on every API response except the direct unsupported-version 400.
required: true
schema:
type: integer
enum:
- 300
RateLimitReset:
description: Seconds until the current API window resets, clamped to at least one. Present on every API response except the direct unsupported-version 400.
required: true
schema:
type: integer
minimum: 1
maximum: 60
externalDocs:
description: Agent manifest, MCP endpoint, and call contract
url: https://agentic-atlas.dev/llms.txt