Skip to content

feat(a2a): implement A2A client tools and server (closes #514 phases 1 & 2)#4948

Closed
balaji-embedcentrum wants to merge 1 commit into
NousResearch:mainfrom
balaji-embedcentrum:feat/a2a-client-server-implementation
Closed

feat(a2a): implement A2A client tools and server (closes #514 phases 1 & 2)#4948
balaji-embedcentrum wants to merge 1 commit into
NousResearch:mainfrom
balaji-embedcentrum:feat/a2a-client-server-implementation

Conversation

@balaji-embedcentrum

@balaji-embedcentrum balaji-embedcentrum commented Apr 4, 2026

Copy link
Copy Markdown

Summary

Closes #514 — implements Phases 1 and 2 of the A2A (Agent-to-Agent) protocol support.

Phase 1 — A2A Client (tools/a2a_tool.py)

Three new tools in the a2a toolset:

  • a2a_discover — fetch an Agent Card from any A2A endpoint; results cached for 5 min to avoid redundant fetches
  • a2a_call — send a task to a remote A2A agent; auto-detects streaming capability from the cached Agent Card and uses tasks/sendSubscribe (SSE) when supported, falling back to tasks/send
  • a2a_local_scan — scan a localhost port range (default 9000–9010) to discover running A2A agents without any pre-configuration; closes the discovery gap identified in the issue

Named agents can be pre-configured in ~/.hermes/config.yaml:

a2a_agents:
  researcher:
    url: http://192.168.1.100:9000
    bearer_token: "optional"

Phase 2 — A2A Server (a2a_adapter/)

Exposes Hermes as a standards-compliant A2A agent over HTTP:

  • HermesAgentExecutor wraps AIAgent.run_conversation() with full SSE streaming support
  • Bearer token auth via A2A_KEY env var
  • Agent Card built from env vars (AGENT_NAME, AGENT_SKILLS, AGENT_DESCRIPTION, etc.)
  • Runs as a separate uvicorn process on configurable port (default 9000)
pip install 'hermes-agent[a2a]'
AGENT_NAME=myagent AGENT_SKILLS="coding,analysis" hermes-a2a

Supporting changes

  • pyproject.toml[a2a] optional extra, hermes-a2a CLI entry point, a2a_adapter in packages
  • toolsets.pya2a toolset definition + all 3 tools registered in _HERMES_CORE_TOOLS

Docs & Tests

  • docs/a2a-user-guide.md — end-user guide covering server setup, client tools, multi-agent workflows, auth, and troubleshooting
  • docs/a2a-architecture.md — internal design, data flow diagrams, extension points
  • tests/tools/test_a2a_tool.py — unit tests for all 3 tools using mocks (no real servers needed); covers caching, SSE streaming, named agent resolution, error handling

What's not in this PR (Phase 3)

Multi-agent orchestration patterns (agent registry, automatic agent selection, fan-out workflows) remain open per the original issue roadmap.

How to test manually

1. Start the A2A server:

pip install 'hermes-agent[a2a]'
AGENT_NAME=myagent AGENT_SKILLS="coding,analysis,reasoning" hermes-a2a

2. Verify the Agent Card:

curl http://localhost:9000/.well-known/agent.json | jq

3. Send a test task:

curl -s -X POST http://localhost:9000 \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":"1","method":"tasks/send","params":{"id":"t1","message":{"role":"user","parts":[{"type":"text","text":"what is 2+2?"}]}}}' \
  | jq .result.artifacts[0].parts[0].text

4. Test client tools in chat:

hermes chat --toolsets hermes-core,a2a
# Then: "find all local agents" → triggers a2a_local_scan
# Then: "discover the agent at http://localhost:9000" → triggers a2a_discover
# Then: "ask the agent at http://localhost:9000 what is 2+2?" → triggers a2a_call

5. Run unit tests:

pytest tests/tools/test_a2a_tool.py -v

Platforms tested

  • macOS (Darwin 25.3.0) — server started, Agent Card served, tasks/send returned correct response, SSE streaming verified end-to-end against live deployment at http://15.204.116.57:8106

Test plan

  • pip install 'hermes-agent[a2a]' installs without errors
  • hermes-a2a starts and serves Agent Card at /.well-known/agent.json
  • tasks/send returns a completed response
  • tasks/sendSubscribe streams SSE events correctly
  • a2a_discover, a2a_call, a2a_local_scan available in chat with a2a toolset enabled
  • pytest tests/tools/test_a2a_tool.py passes in full dev environment
  • Tested on Linux

Related issues

…#514 phases 1 & 2)

Phase 1 — A2A Client (tools/a2a_tool.py):
- Add a2a_discover: fetch and cache Agent Cards from remote A2A endpoints
- Add a2a_call: send tasks via tasks/send (non-streaming) or
  tasks/sendSubscribe (SSE streaming), auto-detected from Agent Card
- Add a2a_local_scan: scan localhost port range to discover running A2A
  agents without pre-configuration
- Agent card caching (5 min TTL) shared across discover and call
- Named agent resolution from ~/.hermes/config.yaml a2a_agents section

Phase 2 — A2A Server (a2a_adapter/):
- HermesAgentExecutor wrapping AIAgent.run_conversation()
- Streaming via SSE (tasks/sendSubscribe) with delta queue bridge
- Bearer token auth via A2A_KEY env var
- Agent Card built from env vars (AGENT_NAME, AGENT_SKILLS, etc.)
- Separate uvicorn process on configurable port (default 9000)
- CLI entry point: hermes-a2a / python -m a2a_adapter

Supporting changes:
- pyproject.toml: [a2a] extra, hermes-a2a entry point, a2a_adapter package
- toolsets.py: a2a toolset definition + all 3 tools in _HERMES_CORE_TOOLS

Docs & tests:
- docs/a2a-user-guide.md: end-user guide for server and client usage
- docs/a2a-architecture.md: internal design, data flow, extension points
- tests/tools/test_a2a_tool.py: unit tests for all 3 tools using mocks

Co-Authored-By: balaji-embedcentrum <balaji@embedcentrum.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Feature: A2A (Agent-to-Agent) Protocol Support — Remote Agent Discovery, Communication & Interoperability

1 participant