Files
cleveragents-core/docs/reference/a2a.md
T
HAL9000 18d00c04c4
CI / lint (pull_request) Failing after 1m15s
CI / quality (pull_request) Successful in 1m21s
CI / typecheck (pull_request) Successful in 1m34s
CI / security (pull_request) Successful in 1m37s
CI / coverage (pull_request) Has been skipped
CI / unit_tests (pull_request) Failing after 1m37s
CI / docker (pull_request) Has been skipped
CI / build (pull_request) Successful in 33s
CI / helm (pull_request) Successful in 26s
CI / push-validation (pull_request) Successful in 19s
CI / e2e_tests (pull_request) Successful in 3m20s
CI / integration_tests (pull_request) Successful in 4m32s
CI / status-check (pull_request) Failing after 3s
fix(skills): implement multi-scope agent skill discovery for global, project, and local tiers
Implements AgentSkillDiscovery class to support discovering Agent Skills from
multiple configured directories across three scopes (global, project, local).
Handles name collisions with precedence: local > project > global.

Adds comprehensive BDD test coverage for multi-scope discovery scenarios including:
- Global-only, project-only, and local-only discovery
- Combined discovery from all scopes
- Name collision resolution with proper precedence
- Non-existent and empty scope directory handling
- Multiple skills in same scope discovery

ISSUES CLOSED: #9369
2026-05-06 19:55:22 +00:00

16 KiB

A2A (Agent-to-Agent Protocol) Reference

Overview

CleverAgents adopts the external Agent-to-Agent (A2A) Protocol standard (a2a-protocol.org) as the sole communication protocol for all client-server interaction. A2A provides the boundary layer between the Presentation and Application layers.

Module: cleveragents.a2a Protocol: JSON-RPC 2.0 binding (A2A specification Section 9) SDK: a2a-sdk package (a2aproject/a2a-python)

Table of Contents


Agent Card

A2A uses Agent Cards for capability discovery. The CleverAgents Agent Card is served at /.well-known/agent.json in server mode:

{
  "name": "CleverAgents",
  "description": "AI agent orchestration platform",
  "url": "https://server.example.com",
  "version": "1.0",
  "capabilities": {
    "streaming": true,
    "pushNotifications": true
  },
  "skills": [
    { "id": "plan-lifecycle", "name": "Plan Lifecycle Management" },
    { "id": "registry-crud", "name": "Entity Registry Operations" },
    { "id": "context-mgmt", "name": "Context Assembly" },
    { "id": "entity-sync", "name": "Entity Synchronization" },
    { "id": "namespace-mgmt", "name": "Namespace Management" }
  ],
  "extensions": [
    {
      "uri": "urn:cleveragents:extensions:v1",
      "description": "CleverAgents platform operations"
    }
  ],
  "securitySchemes": [
    { "type": "http", "scheme": "bearer" }
  ],
  "interfaces": [
    { "protocol": "jsonrpc", "url": "https://server.example.com/a2a" }
  ]
}

An authenticated extended Agent Card with additional detail is available via the getExtendedAgentCard operation.


Transport Modes

Mode Transport Class / SDK Component Behaviour
Local A2A JSON-RPC over stdio A2aLocalFacade + JSON-RPC stdio Agent as subprocess; extensions resolved in-process
Server A2A JSON-RPC over HTTP A2A SDK HTTP transport JSON-RPC 2.0 to CleverAgents server

In local mode the agent runs as a subprocess. JSON-RPC messages flow over stdin/stdout. Extension methods (_cleveragents/*) are intercepted by A2aLocalFacade and routed to in-process Application-layer services. No network, no authentication.

In server mode the client connects via the A2A SDK's HTTP transport. All operations — standard A2A and extensions — flow through the single A2A JSON-RPC 2.0 endpoint on the server.


Standard A2A Operations

These operations are defined by the external A2A specification and handle the core agent interaction lifecycle:

Operation Direction Purpose
message/send Client -> Server Send a message to the agent; returns a Task or direct Message
message/stream Client -> Server Send a message with SSE streaming of task updates
tasks/get Client -> Server Retrieve current state of a task
tasks/list Client -> Server List tasks with optional filtering and pagination
tasks/cancel Client -> Server Cancel a running task
tasks/subscribe Client -> Server Subscribe to task updates via SSE
pushNotificationConfig/create Client -> Server Create push notification webhook
pushNotificationConfig/get Client -> Server Get push notification config
pushNotificationConfig/list Client -> Server List push notification configs
pushNotificationConfig/delete Client -> Server Delete push notification config
getExtendedAgentCard Client -> Server Fetch authenticated Agent Card

Extension Methods

Platform operations use _cleveragents/-prefixed extension methods (declared in the Agent Card via the A2A extension mechanism):

Plan Operations

Method Service Method Required Params
_cleveragents/plan/use PlanService.create_plan() action_name, project_names
_cleveragents/plan/execute PlanLifecycle.execute() plan_id
_cleveragents/plan/apply PlanLifecycle.apply() plan_id
_cleveragents/plan/cancel PlanService.cancel() plan_id
_cleveragents/plan/status PlanService.get_status() plan_id
_cleveragents/plan/tree PlanService.get_tree() plan_id
_cleveragents/plan/explain PlanService.explain_decision() plan_id, decision_id
_cleveragents/plan/correct CorrectionFlow.correct() plan_id, decision_id, correction
_cleveragents/plan/diff PlanService.get_diff() plan_id
_cleveragents/plan/artifacts PlanService.get_artifacts() plan_id
_cleveragents/plan/prompt PlanService.inject_guidance() plan_id, message
_cleveragents/plan/rollback PlanLifecycle.rollback() plan_id
_cleveragents/plan/list PlanService.list() (optional filters)

Registry Operations

Pattern applies to all entity types (actor, skill, tool, validation, resource, resource_type, project, action, automation_profile, invariant, lsp):

Method Pattern Service Method Pattern Required Params
_cleveragents/registry/{entity}/list {Entity}Service.list() namespace (optional)
_cleveragents/registry/{entity}/show {Entity}Service.show() name
_cleveragents/registry/{entity}/add {Entity}Service.add() Entity-specific fields
_cleveragents/registry/{entity}/update {Entity}Service.update() name, updated fields
_cleveragents/registry/{entity}/remove {Entity}Service.remove() name

Context Operations

Method Service Method Required Params
_cleveragents/context/show ContextService.show() project_name
_cleveragents/context/inspect ContextService.inspect() project_name
_cleveragents/context/simulate ContextService.simulate() project_name, simulation params
_cleveragents/context/set ContextService.set() project_name, context data

Sync Operations

Method Service Method Required Params
_cleveragents/sync/pull SyncService.pull() namespace
_cleveragents/sync/push SyncService.push() namespace, entities
_cleveragents/sync/status SyncService.status() namespace (optional)

Namespace Operations

Method Service Method Required Params
_cleveragents/namespace/list NamespaceService.list() --
_cleveragents/namespace/show NamespaceService.show() namespace
_cleveragents/namespace/members NamespaceService.members() namespace

Health and Diagnostics

Method Purpose
_cleveragents/health/check Server health check
_cleveragents/diagnostics/run Run diagnostic suite

Streaming Events

A2A streaming uses SSE via the message/stream operation, delivering typed events as the task progresses:

Event Type Emitted When
TaskStatusUpdateEvent Task state changes (submitted -> working -> completed, etc.)
TaskArtifactUpdateEvent Agent produces output (response chunks, plan entries, tool results)

Task Lifecycle States

State Meaning
submitted Task created, awaiting processing
working Agent is actively processing
input-required Agent needs client input (human-in-the-loop)
completed Task finished successfully
failed Task failed with error
canceled Task was canceled by client
rejected Task was rejected by agent

Example Streaming Event

{
  "jsonrpc": "2.0",
  "method": "message/stream",
  "params": {
    "id": "task_01HXR...",
    "status": { "state": "working" },
    "artifacts": [{
      "parts": [{ "text": "I'll start by extracting..." }]
    }]
  }
}

Multi-Turn Interactions

A2A replaces protocol-level callbacks with multi-turn interactions via the Task lifecycle:

Interaction How It Works
Human-in-the-loop approval Task enters input-required state; client displays prompt; client responds via message/send
File access (read/write) _cleveragents/fs/* extension methods handled locally by client
Terminal access _cleveragents/terminal/* extension methods handled locally by client

When a server-hosted agent needs client-side resources, the Task enters input-required state. The client handles the request and responds, resuming the task.


Local Facade

A2aLocalFacade handles extension method dispatch in local mode:

from cleveragents.a2a import A2aLocalFacade
from cleveragents.a2a.models import A2aRequest

facade = A2aLocalFacade(services={
    "session_service": my_session_service,
    "plan_lifecycle_service": my_plan_lifecycle_service,
    "tool_registry": my_tool_registry,
    "resource_registry_service": my_resource_registry_service,
})

# Extension methods are dispatched to in-process services (synchronous)
response = facade.dispatch(A2aRequest(
    method="_cleveragents/plan/status",
    params={"plan_id": "01J..."}
))

Constructor

Parameter Type Default Description
services dict[str, Any] | None None Named services for routing

Methods

Method Returns Description
dispatch(request: A2aRequest) A2aResponse Route extension method to handler
register_service None Register a named service
list_operations() list[str] All supported extension method names

Service Wiring

Each A2A extension method is wired to a concrete application service. Services are injected via the services dict at construction time or registered later with register_service().

Service Keys

Key Type Wired Methods
session_service SessionWorkflow Standard message operations
plan_lifecycle_service PlanLifecycleService _cleveragents/plan/*
tool_registry ToolRegistry _cleveragents/registry/tool/*
resource_registry_service ResourceRegistryService _cleveragents/registry/resource/*
sync_service SyncService _cleveragents/sync/*
namespace_service NamespaceService _cleveragents/namespace/*
context_service ContextService _cleveragents/context/*

Error Code Taxonomy

Domain exceptions are mapped to JSON-RPC 2.0 error codes:

JSON-RPC Code Domain Exception(s) Meaning
-32700 -- Parse error (malformed JSON)
-32600 -- Invalid request
-32601 A2aOperationNotFoundError Method not found
-32602 ValidationError Invalid params
-32603 Any unhandled Exception Internal error
-32001 ResourceNotFoundError Entity not found
-32002 AuthenticationError Authentication required
-32003 AuthorizationError Authorization forbidden
-32004 BusinessRuleViolation Invalid state
-32005 DuplicateEntityError Already exists
-32006 BudgetExceededError Budget exceeded
-32007 A2aVersionMismatchError Version mismatch
-32008 PlanError Plan lifecycle error
-32009 ConfigurationError Configuration error

Example Error Response

{
  "jsonrpc": "2.0",
  "id": 42,
  "error": {
    "code": -32001,
    "message": "Plan not found",
    "data": { "plan_id": "01HXRCF1..." }
  }
}

Authentication

Authentication uses standard HTTP security schemes declared in the Agent Card:

  1. Client discovers Agent Card at /.well-known/agent.json
  2. Agent Card's securitySchemes declares supported auth mechanisms
  3. Client authenticates using the declared scheme (e.g., Authorization: Bearer <token>)
  4. All subsequent requests include authentication credentials

Local mode (stdio) bypasses authentication -- the agent subprocess runs with the user's local permissions.


Client Architecture

The client uses an A2aClient wrapping the A2A Python SDK:

from cleveragents.a2a import A2aClient, TransportSelector

# TransportSelector picks stdio or HTTP based on configuration
transport = TransportSelector().get_transport()
client = A2aClient(transport)

# Standard A2A operation
await client.send_message(message="Add pagination", context_id="ctx_01HXR...")

# Extension method
result = await client.plan_status(plan_id="01HXRCF1...")

Components

Component Role Notes
A2aLocalFacade Extension dispatch in local mode Routes _cleveragents/ methods to in-process services
A2A SDK HTTP transport Server mode transport Production HTTP transport with SSE streaming
A2A SDK JSON-RPC types Wire format SendMessageRequest, Task, Message, Part, etc.
A2aEventQueue Local mode event delivery In-process task update event delivery
Agent Card Discovery Capability advertisement and auth scheme declaration

Error Hierarchy

CleverAgentsError
  └── A2aError
        ├── A2aNotAvailableError
        ├── A2aVersionMismatchError
        └── A2aOperationNotFoundError
Exception When Raised
A2aNotAvailableError Server-mode operation attempted without connection
A2aVersionMismatchError Unsupported A2A version
A2aOperationNotFoundError Unknown method dispatched