Sprinter Docs

External Agents

Connecting to external AI agents via OpenClaw, A2A protocol, and MCP -- connection lifecycle, delegation, and administration.

External Agents

The Sprinter Platform supports connections to external AI agents and services through three protocols: OpenClaw (OpenAI-compatible API), A2A (Agent-to-Agent protocol), and MCP (Model Context Protocol). Additional source-type connections (RSS, API, Authenticated Web) enable data ingestion from external services.

Connection types

TypeProtocolTest endpointUse case
openclawOpenAI-compatible API/v1/modelsExternal LLM agents via OpenClaw gateway
a2aAgent-to-Agent/.well-known/agent-card.jsonGoogle A2A protocol agents
mcpModel Context Protocol/tools/list (POST, JSON-RPC)MCP tool servers
rssRSS/Atom feedsFeed URLContent ingestion from RSS feeds
apiREST APIBase URLJSON API data sources
authenticated_webHTTP with authBase URLAuthenticated website scraping

The first three (openclaw, a2a, mcp) are agent gateway types -- they proxy to external agents that can receive delegated tasks. The remaining three are data source types used by the source sync system for content ingestion.

Database schema

Connections are stored in the agent_connections table:

ColumnTypePurpose
iduuidPrimary key
tenant_iduuidTenant scope
nametextDisplay name
connection_typetextOne of the six connection types
base_urltextBase URL for the external service
encrypted_credentialstextAES-encrypted credentials blob (never returned via API)
configjsonbAdditional configuration (custom headers, test path, user agent)
statustextactive, inactive, or error
last_health_checktimestamptzLast successful health check
last_errortextLast error message
created_byuuidUser who created the connection

Credentials are encrypted at rest using encryptCredentials() from lib/crypto/credentials.ts. The API-facing type (AgentConnection) redacts credentials to a boolean hasCredentials field via toPublicConnection().

Connection lifecycle

1. Create

Create a connection via Admin > Connections or the API:

POST /api/agent-connections
{
  "name": "My OpenClaw Agent",
  "connection_type": "openclaw",
  "base_url": "https://agent.example.com",
  "credentials": { "apiKey": "sk-..." },
  "config": { "testPath": "/v1/models" }
}

Credentials are encrypted before storage. The config object supports:

  • testPath -- custom endpoint for health checks (overrides the protocol default)
  • userAgent -- custom User-Agent header
  • headers -- additional HTTP headers as key-value pairs
  • oauth -- optional provider metadata for generic OAuth 2 connections
  • oauthScopes -- optional scope override for OAuth-backed connections

2. Test

Test connectivity and credentials:

POST /api/agent-connections/:id/test

The test endpoint sends a protocol-appropriate request:

  • OpenClaw: GET to /v1/models
  • A2A: GET to /.well-known/agent-card.json
  • MCP: POST JSON-RPC tools/list to the base URL
  • RSS/API/Web: GET to the base URL

On success, updates status to active and records last_health_check. On failure, updates status to error and stores the error message.

Requests have a 10-second timeout. Credentials (token, API key, cookie, or custom headers) are decrypted and applied to the request automatically.

OAuth connect / refresh

Some provider presets now support an OAuth authorization-code flow directly from the Connections UI. The same agent_connections row stores:

  • encrypted client credentials and tokens in encrypted_credentials
  • public connection state in config.oauthStatus, config.oauthConnectedAt, config.oauthExpiresAt, and config.oauthScope

Routes:

GET  /api/agent-connections/:id/oauth/start
GET  /api/agent-connections/:id/oauth/callback
POST /api/agent-connections/:id/oauth/refresh

The current preset-backed OAuth connectors are Canva, Dropbox, Google Analytics, and LinkedIn. Other providers can still use the same flow by supplying config.oauth in advanced JSON.

3. Discover

For A2A connections, discover available agents:

POST /api/agent-connections/:id/discover

Returns a list of DiscoveredAgent objects with externalAgentId, name, description, and whether the agent has already been imported.

4. Update and delete

PATCH /api/agent-connections/:id
DELETE /api/agent-connections/:id

Updates can change the name, URL, credentials, config, or status. Deleting a connection removes it permanently.

Server actions

Connection CRUD is also available via server actions in features/agents/server/connection-actions.ts:

  • getConnections() -- list all connections for the current tenant
  • getConnectionById(id) -- fetch a single connection (API-safe, credentials redacted)
  • getConnectionByIdInternal(id) -- fetch with encrypted credentials (server-only)
  • createConnection(input) -- create with Zod-validated input
  • updateConnection(id, input) -- partial update
  • deleteConnection(id) -- remove
  • testConnection(id) -- health check with status update

MCP connections in chat agents

When an admin creates an MCP connection and sets its status to active, that connection is automatically available to chat agents the next time a message is sent. No code change or agent reconfiguration is needed.

Chat agents receive two gateway tools — listMcpTools and callMcpTool — that are assembled at request time from the tenant's active MCP connections. This is the only way MCP servers surface to internal agents; there is no separate "enable MCP" toggle on an agent.

The flow from connection to agent use:

  1. Admin creates an MCP connection in Admin > Connections (connection type: MCP) and tests it.
  2. On the next chat request, getMcpServerConfigs(tenantId) fetches active MCP connections (cached cross-request, invalidated after any mutation).
  3. createMcpGatewayTools(configs) produces listMcpTools and callMcpTool with the server names embedded in the description prefix.
  4. The agent's ToolSet contains exactly 2 MCP-related tools regardless of how many MCP servers are connected.
  5. During the conversation the agent calls listMcpTools to discover available tools, then callMcpTool to execute them.

Context cost is always 2 tool slots. MCP tool schemas are fetched lazily only when the agent calls listMcpTools, not at ToolSet assembly time. This keeps the prompt prefix stable and preserves Anthropic prompt caching.

Credential resolution. The gateway resolves all auth headers from the connection's encrypted credentials using resolveConnectionAuthHeaders(). Any credential type supported by the shared resolver (Bearer, cookie, basic, custom headers) works out of the box — no special MCP-specific auth configuration is needed.

Autonomous paths (heartbeat, extraction, workflows) are excluded by default. These paths pass an empty config list, so no MCP gateway tools are injected. This is intentional: autonomous runs execute without human oversight, and MCP tool calls reach external services. Opting in requires an explicit code change to pass mcpConfigs in those paths.

Agent delegation

Agents can delegate tasks to other agents (internal or external) via the delegation tool, which is automatically included in every agent's tool set.

The delegation factory at features/agents/lib/delegate.ts creates a delegateToAgent tool:

const delegateTool = createDelegateToAgentTool();
// Agents call: delegateToAgent({ agentSlug: "researcher", task: "Find market data for..." })

Internal delegation: Resolves the target agent from the code registry, runs it inline within the same process.

External delegation: Looks up the target agent via agent_connections, routes the task through the connection-based provider (OpenClaw or A2A protocol). Supports configurable timeouts for external calls.

Credential types

The encrypted credentials blob supports several authentication patterns:

PatternFieldsHeader applied
OAuth 2{ scheme: "oauth2", oauth2: { clientId, clientSecret, accessToken, refreshToken } }Authorization: Bearer <accessToken>
Bearer token{ token: "..." }Authorization: Bearer <token>
API key{ apiKey: "..." }Authorization: Bearer <apiKey>
Cookie{ cookie: "..." }Cookie: <cookie>
Basic auth{ basicAuth: { username, password } }Authorization: Basic <base64>
Custom headers{ headers: { "X-Custom": "..." } }Applied directly

Multiple credential types can be combined in a single connection.

Zod validation schemas

All API inputs are validated with Zod schemas defined in features/agents/connection-types.ts:

  • CreateConnectionSchema -- validates name (1-255 chars), connection_type (enum), base_url (valid URL), optional credentials and config
  • UpdateConnectionSchema -- all fields optional for partial updates

Administration

The Connections tab in Admin (/admin > Connections) provides:

  • Table view of all connections with status indicators (green dot for active, gray for inactive, red for error)
  • Badge indicating connection type (OpenClaw, A2A, MCP, RSS, API, Authenticated Web)
  • Capability toggles so a single connection can be used for source monitoring, publishing, external agent runtime, or a combination of those roles
  • Browser monitoring agent ID field for source-capable OpenClaw/A2A connections
  • OAuth connect, reconnect, and token refresh actions for supported providers
  • Test button for each connection with inline result display
  • Add/edit dialog with credential input
  • Last health check timestamp and error message display
  • Delete with confirmation

Source connections

RSS, API, and Authenticated Web connections are used by the source sync system (features/source-sync/) to ingest external content into the entity graph. These connections provide:

  • Authentication for paywalled or private content sources
  • Custom headers and user agent configuration
  • Domain and keyword filtering
  • Deduplication with configurable time windows

Source entities reference connections via their content.connection_id field. The source sync function resolves the connection, decrypts credentials, and uses them when fetching content.

Browser-agent source monitoring

Some sites are too dynamic or hostile for plain HTTP scraping. In those cases a source can use the browser scrape strategy and point to a source-capable OpenClaw or A2A connection instead of an HTTP data-source connection.

Expected connection config:

  • config.capabilities includes source
  • config.browserAgentId (or config.externalAgentId) names the external browser-capable agent to invoke

The Admin UI exposes this directly: select a gateway connection, enable the Source monitoring capability, and enter the browser agent's external ID. That makes existing gateway agents such as Chippy reusable for monitored-source jobs without creating a second browser-only connection model.

This keeps browser monitoring on the same connection primitive as the rest of the platform instead of introducing a second browser-specific credential model.

Connect your agents (quick start)

Three steps to connect any MCP-compatible agent to Amble:

  1. Create an API key in Admin > API Keys with scopes: tools:execute, skills:read, views:read
  2. Point your agent at {AMBLE_URL}/api/mcp/server with the key as a Bearer token
  3. Verify with a curl test:
curl -X POST https://app.sprinter.ai/api/mcp/server \
  -H "Authorization: Bearer sk_..." \
  -H "Content-Type: application/json" \
  -H "MCP-Protocol-Version: 2025-03-26" \
  -d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-03-26","capabilities":{},"clientInfo":{"name":"test","version":"0.1.0"}}}'

A successful response returns {"jsonrpc":"2.0","id":1,"result":{...}} with server capabilities.

For production use at app.sprinter.ai, replace localhost:3000 in all examples below with your deployment URL.

Local interoperability endpoints

Amble exposes two complementary surfaces for external agent/app consumers:

1. Standard MCP server (preferred for Codex / Claude Code / OpenClaw)

  • POST /api/mcp/server
  • GET /api/mcp/server
  • DELETE /api/mcp/server

This is a real streamable HTTP MCP server backed by Amble tools. Point local coding agents here.

API-key scopes control what the MCP server exposes:

  • tools:execute — exposes tenant-accessible Amble tools
  • skills:read — exposes helper tools:
    • amble_list_skills
    • amble_get_skill
  • views:read — exposes helper tools:
    • amble_list_views
    • amble_get_view

2. App/CLI-friendly REST + JSON-RPC primitives

  • POST /api/mcp/tools — JSON-RPC tools/list / tools/call
  • GET /api/skills — list skills (skills:read)
  • GET /api/skills/:id — fetch skill by id (skills:read)
  • GET /api/skills/slug/:slug — fetch skill by slug (skills:read)
  • GET /api/views — list views (views:read)
  • GET /api/views/:id — fetch view by id (views:read)

These are useful for simple scripts, app integrations, and CLI workflows where a full MCP client is unnecessary.

Authentication

Authentication is API-key based:

  • Authorization: Bearer sk_...
  • X-API-Key: sk_...

Recommended local-agent key scopes:

  • tools:execute
  • skills:read
  • views:read

Add entities:read and entity-types:read if the consuming app also needs direct record/schema access.

Setup recipes

Set AMBLE_BASE_URL to your deployment (e.g. https://app.sprinter.ai for production, http://localhost:3000 for local dev).

Codex

export AMBLE_BASE_URL="https://app.sprinter.ai"
export AMBLE_API_KEY="sk_..."
codex mcp add amble --url "$AMBLE_BASE_URL/api/mcp/server" --bearer-token-env-var AMBLE_API_KEY

Claude Code

export AMBLE_BASE_URL="https://app.sprinter.ai"
export AMBLE_API_KEY="sk_..."
claude mcp add --transport http amble "$AMBLE_BASE_URL/api/mcp/server" --header "Authorization: Bearer $AMBLE_API_KEY"

OpenClaw ACP agents

Configure the ACP plugin's mcpServers to point at Amble's MCP server:

{
  "plugins": {
    "entries": [
      {
        "type": "acpx",
        "enabled": true,
        "config": {
          "mcpServers": {
            "amble": {
              "type": "http",
              "url": "https://app.sprinter.ai/api/mcp/server",
              "headers": {
                "Authorization": "Bearer sk_..."
              }
            }
          }
        }
      }
    ]
  }
}

If you want secrets managed outside the raw config, use OpenClaw's secrets/env mechanisms and inject the bearer token there instead of hard-coding it.

CLI bootstrap

Use the Amble CLI to validate and bootstrap local setups:

pnpm cli doctor --base-url http://localhost:3000 --api-key sk_...
pnpm cli config codex --base-url http://localhost:3000 --api-key sk_...
pnpm cli config claude --base-url http://localhost:3000 --api-key sk_...
pnpm cli mcp list --base-url http://localhost:3000 --api-key sk_...
pnpm cli mcp call my-tool --payload '{"foo":"bar"}' --api-key sk_...
pnpm cli skills --base-url http://localhost:3000 --api-key sk_...
pnpm cli skills get my-skill --base-url http://localhost:3000 --api-key sk_...
pnpm cli views --base-url http://localhost:3000 --api-key sk_...

Chippy rollout checklist

When rolling this out to Chippy later:

  1. Mint a dedicated API key for Chippy.
  2. Scope it to the minimum required capabilities.
  3. Point Chippy to /api/mcp/server.
  4. Validate with pnpm cli doctor against the target environment.
  5. Verify tool execution + skill fetch + view fetch before turning on autonomous runs.

On this page