Transport-level routing for MCP/ACP protocols
We appreciate your patience. The service is temporarily operating in an external runtime environment.
Transport-level routing for MCP/ACP protocols
We appreciate your patience. The service is temporarily operating in an external runtime environment.
Universal worker for spawning agents from the ACP Registry on demand.
The Registry Launcher provides dynamic agent routing capabilities by integrating with the ACP Registry. It automatically discovers available agents, manages their lifecycle as child processes, and routes messages based on the requested agentId. This enables a single stdio Bus deployment to support multiple agents without manual configuration.
Location: workers-registry/acp-worker/src/registry-launcher/
sessionId route to the same agent instanceThe Registry Launcher can route to any agent in the ACP Registry, including:
claude-acp - Claude Agentgoose - Goosecline - Clinegithub-copilot - GitHub CopilotThe full list of available agents is dynamically fetched from the registry at runtime.
Create a configuration file for stdio Bus kernel:
{"pools": [{"id": "registry-launcher","command": "npx","args": ["@stdiobus/workers-registry","registry-launcher"],"instances": 1}]}
For agents that require API keys (like Claude), provide a separate API keys file:
{"pools": [{"id": "registry-launcher","command": "npx","args": ["@stdiobus/workers-registry","registry-launcher","./api-keys.json"],"instances": 1}]}
API Keys File Format (api-keys.json):
{"agents": {"claude-acp": {"apiKey": "sk-ant-...","env": {}},"goose": {"apiKey": "sk-...","env": {}},"github-copilot": {"apiKey": "ghp_...","env": {}}},"version": "1.0.0"}
The Registry Launcher will use these API keys and environment variables for spawned agent processes.
For production deployments with resource limits:
{"pools": [{"id": "registry-launcher","command": "npx","args": ["@stdiobus/workers-registry","registry-launcher","./api-keys.json"],"instances": 2}],"limits": {"max_input_buffer": 2097152,"max_output_queue": 8388608,"max_restarts": 10,"restart_window_sec": 120,"backpressure_timeout_sec": 90}}
| Field | Type | Description |
|---|---|---|
id | string | Unique identifier for the worker pool |
command | string | Path to Node.js executable |
args | string[] | Arguments: launcher path, "registry-launcher", optional API keys file |
instances | number | Number of launcher instances (≥1) |
The Registry Launcher automatically fetches the agent registry from:
https://cdn.agentclientprotocol.com/registry/v1/latest/registry.json
The registry contains metadata for each agent including:
Each agent in the registry includes:
{"id": "claude-acp","name": "Claude Agent","command": "npx","args": ["@agentclientprotocol/claude-acp"],"env": {"ANTHROPIC_API_KEY": "required"}}
The Registry Launcher uses this metadata to spawn and configure agent processes.
The registry is cached locally to minimize network requests. The cache is refreshed:
The Registry Launcher manages agent processes through the following lifecycle:
agentIdThe Registry Launcher manages agent processes:
Messages with the same sessionId are routed to the same agent instance:
{"jsonrpc": "2.0","id": "1","method": "initialize","params": {"agentId": "claude-acp","clientInfo": {"name": "my-client","version": "1.0.0"}},"sessionId": "sess-abc123"}
All subsequent messages with sessionId: "sess-abc123" will route to the same Claude agent instance.
Include the agentId in the request parameters:
{"jsonrpc": "2.0","id": "1","method": "initialize","params": {"agentId": "claude-acp","clientInfo": {"name": "test-client","version": "1.0.0"}}}
agentId parameteragentIdThe Registry Launcher can handle multiple agents simultaneously:
# Client 1 requests Claude{"jsonrpc":"2.0","id":"1","method":"initialize","params":{"agentId":"claude-acp"}}# Client 2 requests Goose{"jsonrpc":"2.0","id":"2","method":"initialize","params":{"agentId":"goose"}}# Both agents run concurrently, managed by the same launcher
{"jsonrpc": "2.0","id": "1","method": "initialize","params": {"agentId": "claude-acp","clientInfo": {"name": "my-client","version": "1.0.0"}}}
{"jsonrpc": "2.0","id": "1","result": {"serverInfo": {"name": "claude-acp","version": "1.0.0"},"capabilities": {"prompts": true,"tools": true}}}
{"jsonrpc": "2.0","id": "2","method": "prompt","sessionId": "sess-abc123","params": {"agentId": "claude-acp","prompt": "What is the weather today?","context": {}}}
Start stdio Bus with the Registry Launcher:
docker run \--name stdiobus-registry-test \-p 9000:9000 \-v $(pwd):/stdiobus:ro \-v $(pwd)/config.json:/config.json:ro \-v $(pwd)/api-keys.json:/api-keys.json:ro \stdiobus/stdiobus:latest \--config /config.json --tcp 0.0.0.0:9000
echo '{"jsonrpc":"2.0","id":"1","method":"initialize","params":{"agentId":"claude-acp","clientInfo":{"name":"test"}}}' | nc localhost 9000
The Registry Launcher will spawn the Claude agent and return its initialization response:
{"jsonrpc":"2.0","id":"1","result":{"serverInfo":{"name":"claude-acp","version":"1.0.0"},"capabilities":{"prompts":true,"tools":true}}}
docker stop stdiobus-registry-test && docker rm stdiobus-registry-test
// Import registry launcherimport { registryLauncher } from '@stdiobus/workers-registry/workers';
import type { RegistryAgent } from '@stdiobus/workers-registry/workers/registry-launcher';// Use types for type-safe developmentconst agent: RegistryAgent = /* ... */;
If the Registry Launcher cannot find an agent:
{"jsonrpc":"2.0","id":"1","error":{"code":-32602,"message":"Agent not found: unknown-agent"}}
Solution: Verify the agent ID exists in the ACP Registry.
If an agent requires an API key that is not provided:
{"jsonrpc":"2.0","id":"1","error":{"code":-32603,"message":"Missing required API key: ANTHROPIC_API_KEY"}}
Solution: Add the required API key to your api-keys.json file.
If the Registry Launcher cannot fetch the registry:
# Check network connectivitycurl https://cdn.agentclientprotocol.com/registry/v1/latest/registry.json
Solution: Ensure the launcher has internet access to fetch the registry.