Skip to main content

Top-level vs. nested primitives

Every AXON primitive is either top-level (it stands alone at the program root) or nested (it only appears inside another construct). The compiler enforces this at parse time: a step declaration outside any flow is a syntax error; a flow declaration inside another flow is too.

This page is the authoritative table. When an agent is unsure where a primitive belongs, it should consult this resource — every decision follows from one row.

How to read this table

  • Surface — the AXON keyword as it appears in source.
  • Top-level if the keyword starts a top-level declaration; if it only appears nested.
  • Lives inside — for nested primitives, the parent construct(s) that may contain it.
  • Category — the family the primitive belongs to (drives the axon.primitives(filter) facet).
  • Since — the cycle that introduced it.

Cognition

SurfaceTop-levelLives insideSince
persona— (referenced by run … as and step … use)v0.1.0
context— (referenced by run … within)v0.1.0
flowv0.1.0
anchor— (referenced by run … constrained_by [...])v0.1.0
tool— (referenced implicitly by the tool surface)v0.1.0
intentv0.1.0
memoryv0.1.0
agentv0.1.0
stepflowv0.1.0
reasonflow (sibling of step) — also step bodyv0.1.0
probeflow, step bodyv0.1.0
validateflowv0.1.0
refineflowv0.1.0
weaveflowv0.1.0
useflow, step headerv0.1.0

Cognitive I/O

SurfaceTop-levelLives insideSince
resourcev1.2.0
fabricv1.2.0
manifestv1.2.0
observev1.2.0
reconcilev1.2.0
leasev1.2.0
ensemblev1.2.0
session— (referenced by socket protocol:)v2.3.0

Data plane

SurfaceTop-levelLives insideSince
axonstorev1.31.0
dataspacev1.31.0
corpusv1.31.0
pixv1.14.0
ledgerv2.12.0
typev0.1.0

Session types & wire

SurfaceTop-levelLives insideSince
sessionv2.3.0
socketv2.3.0
axonendpointv1.23.0
axpointv1.23.0
daemonv1.11.0
mcpv1.24.0+
listenflow, daemon bodyv1.11.0
channelv1.6.0
emitflow, daemon bodyv1.6.0
publishflow, daemon bodyv1.6.0
discoverflow, daemon bodyv1.6.0

The taint keyword is a reserved word in the lexer but has no parser production today (it appears in the epistemic-uncertainty lattice in axon-frontend::epistemic, not as a top-level declaration). If a future cycle introduces a taint <Name> { … } declaration the registry + this table grow together.

Operators

SurfaceTop-levelLives insideSince
shieldv1.13.1
mandatev1.13.1
computev1.12.0
lambdav1.10.0
forgeflowv1.12.0
otsv1.4.0
psychev1.5.2
agentv1.12.0

The logic keyword is a reserved word in the lexer but — like taint (v1.2.0) — has no parser production today. If a future cycle introduces a logic <Name> { … } declaration the registry + this table grow together.

Statements (not primitives, but parsed at flow body)

These are statements an agent treats as the body of a flow. They are NEVER top-level.

SurfaceLives insideWhat it does
if … elseflow bodyConditional branch
for x in …flow bodyBounded iteration
let x = …flow bodyLocal binding
return …flow bodyEarly/explicit return
breakinside forLoop early-exit
continueinside forNext iteration
run …top-level — but it is a binding, not a declarationBinds a flow to a persona+context+anchors
applystep body fieldInvoke another flow

Composition discipline

  • Flows compose by apply, not by nesting. A flow declaration cannot appear inside another flow. Sub-flows are referenced from a step body via apply: <FlowName>.
  • Anchors and shields bind through run, not the flow header. A flow does not list its constraints; the run statement that executes it does, via constrained_by [...].
  • Personas, contexts, and tools are referenced, not redeclared. A flow that uses a persona references it (as <Persona> on the run, or use <Persona> per step). It does not embed a fresh declaration.

For the why behind these rules, read axon://logic/flow_composition.