Active
This document describes the current executable binding path from a flow node to a concrete runtime transport.
Use it when you need to understand or change:
- how
graph.nodes[*]selects an agent - how
agents.agentDefs[*]selects an adapter - how
adapterKind: pi-monois resolved in local preview runtime - how the default starter flow reaches DeepSeek without patching core packages
Read it together with:
docs/adr/002-flow-runtime-extension.mdfor the architecture decisiondocs/specs/001-flow-node-contract.mdfor the structural node and runtime contractpackages/flow-schema/src/schema/flow-definition.tsfor the serialized schema
This spec documents the current implementation, not a future target architecture.
It is intentionally precise about what is executable today versus what is only descriptive metadata.
The executable binding path is:
graph.nodes[*].agentId -> agents.agentDefs[*].agentId -> agentDef.adapterKind -> runtime adapter extension -> concrete adapter transport
flowchart LR
Node[graph.nodes[*]] --> AgentId[node.agentId]
AgentId --> AgentDef[agents.agentDefs[*]]
AgentDef --> AdapterKind[agentDef.adapterKind]
AdapterKind --> Registry[resolveRuntimeAdapter]
Registry --> Adapter[AgentAdapter instance]
Adapter --> Transport{resolveTransport}
Transport --> DeepSeek[DeepSeek-compatible transport]
Transport --> PiMonoHttp[pi-mono HTTP transport]
Rules:
node.agentIdis the executable source of truth for choosing an agent definition.agentDef.adapterKindis the executable source of truth for choosing a runtime adapter extension.layout.nodeBindingsis descriptive metadata for layout-aware tooling and documentation.layout.nodeBindings[*].overridesis currently reserved metadata and is not merged into runtime execution.
In web and studio local preview, a run is driven through the following call chain.
sequenceDiagram
participant UI as AssistantPanel
participant Store as useRuntimeStore.startFlow
participant Scheduler as FlowScheduler
participant Registry as resolveRuntimeAdapter
participant Executor as NodeExecutor
participant Adapter as PiMonoAgentAdapter
participant Transport as DeepSeek or pi-mono transport
UI->>Store: startFlow(flowPath, flow, { userPrompt })
Store->>Scheduler: startRun(flow, input)
loop Each executable node
Scheduler->>Scheduler: collect input ports and turnMode
Scheduler->>Registry: resolveRuntimeAdapter(flow, agentDef)
Registry-->>Scheduler: AgentAdapter
Scheduler->>Executor: executeNode(node, flow, adapter, snapshot)
Executor->>Executor: resolveSessionId(runId + agentId)
Executor->>Executor: resolvePrompt(node.config, modelProfile, run input)
Executor->>Adapter: runTurn(invocation)
Adapter->>Transport: createSession() and runTurn()
Transport-->>Adapter: finalText, structuredOutput, usage
Adapter-->>Executor: AgentTurnResult
Executor-->>Scheduler: result
Scheduler->>Scheduler: set node output and propagate ports
end
Responsibilities:
useRuntimeStore.startFlow(...)is the UI entry point.FlowSchedulerowns graph traversal, node dispatch, and port propagation.NodeExecutorowns prompt resolution, session reuse, and invocation shaping.AgentAdapterowns provider-specific turn execution.RunContextstores runtime outputs, and UI debug state is derived from that runtime state.
@agentsflow/pi-mono-runtime currently supports two transport modes behind the same adapterKind: pi-mono extension point.
| Mode | Trigger | Transport Behavior | Typical Use |
|---|---|---|---|
| DeepSeek-compatible | adapterConfig.transport = deepseek or a DeepSeek base URL |
synthetic createSession() and POST /chat/completions |
browser preview and default starter flow |
| pi-mono HTTP backend | any other pi-mono-compatible base URL | POST /sessions, POST /turns, optional abort and dispose |
future real pi-mono service integration |
Design implications:
- switching providers should not require changing
FlowScheduleror the flow graph model - the stable extension boundary is
adapterKind: pi-mono - transport switching happens inside
@agentsflow/pi-mono-runtime, not in flow-schema or flow-engine
The default starter flow currently binds:
main-prompt->main-agentsub-execute->sub-agentmain-evaluate->main-agent
The matching agentDefs currently use:
adapterKind: pi-monoadapterConfig.transport: deepseekmodelProfile.model: deepseek-v4-flash
That means the default starter flow already exercises the pi-mono extension path, while still using the DeepSeek-compatible transport in environments that do not have a real pi-mono backend.
For the current pi-mono runtime, configuration resolves in this order:
- flow or agent
adapterConfig - adapter constructor options
VITE_AGENTSFLOW_PI_MONO_*orAGENTSFLOW_PI_MONO_*VITE_AGENTSFLOW_LLM_*fallback values
This precedence allows the default starter flow to run in browser preview with the repo-level DeepSeek environment file, while still permitting a future real pi-mono backend override.
When a node specifies agentRef, the binding path extends through the PromptAssetManifest:
flowchart LR
Node[graph.nodes[*]] --> AgentRef{node.agentRef?}
AgentRef -->|present| Manifest[PromptAssetManifest]
Manifest --> ResolvedAgent[ResolvedAgentAsset]
ResolvedAgent --> AdapterKind[agent.adapterKind]
AdapterKind --> Registry[resolveRuntimeAdapter]
Registry --> Adapter[AgentAdapter instance]
Adapter --> Transport{resolveTransport}
AgentRef -->|absent| AgentId[node.agentId]
AgentId --> AgentDef[agents.agentDefs[*]]
AgentDef --> AdapterKind2[agentDef.adapterKind]
AdapterKind2 --> Registry2[resolveRuntimeAdapter]
Registry2 --> Adapter2[AgentAdapter instance]
Adapter2 --> Transport2{resolveTransport}
Rules:
- When
node.agentRefis present, resolution goes through thePromptAssetManifest. - When
node.agentRefis absent, resolution falls through to the existingagentId → agentDefspath. - Both paths converge at
adapterKind → runtime adapter extension → transport. agentReftakes precedence overagentIdwhen both are present.
Full specification: docs/specs/003-agents-flow-repo-spec.md.
- This document does not make
layout.nodeBindings[*].overridesexecutable. - This document does not define the wire protocol of a future real pi-mono service beyond the currently expected endpoints.
- This document does not replace ADR 002 or the flow node contract; it narrows the runtime binding topic into one maintenance surface.