Skip to main content

A2A server for AWS Bedrock AgentCore agents

Project description

AWS Bedrock AgentCore A2A Proxy

A2A proxy server for AWS Bedrock AgentCore agents.

This server connects to a given AWS account, discovers AgentCore agents, and then exposes them via A2A. This allows you to call your AgentCore agents over the A2A protocol. Each exposed agent has its own agent card and A2A address.

┌─────────────┐    ┌─────────────────┐    ┌─────────────────┐
│   A2A       │───▶│  A2A Proxy      │───▶│   AgentCore     │
│   Client    │    │                 │    │                 │
│             │◀───│                 │◀───│                 │
└─────────────┘    └─────────────────┘    └─────────────────┘
                           │
                           ▼
                   Auto-discovers agents
                   Exposes A2A endpoints

Features:

  • Expose any Bedrock agent via A2A
  • Automatic polling to discover Bedrock agents
  • Endpoints to show all agents available
  • Invoke agent via A2A
  • Streaming responses

Quickstart

Setup your AWS credentials by editing .env:

# Configure environment
cp .env.example .env
vi .env

Start the AWS Bedrock A2A Proxy with:

make dev

Any agents available for the user with the given credentials will be exposed. If you need to create some agents as an example, set up the required AWS infrastructure and deploy some sample agents:

# Set up demo AWS infrastructure (IAM roles, ECR, CloudWatch, etc.)
make install-demo-infrastructure

# Deploy sample agents using the infrastructure
make install-demo-agents

Calling Bedrock Agents via A2A

View the API documentation:

open http://localhost:2972/docs

List available A2A agents:

curl http://localhost:2972/a2a/agents

# [{"agent_id": "Bedrock_Customer_Support_Agent-jQwAm25rmZ", "name": "Bedrock_Customer_Support_Agent", "host": "localhost:2972", "endpoint": "/a2a/agent/Bedrock_Customer_Support_Agent-jQwAm25rmZ", ...}]

Note: jq is required for the following commands. Install with: brew install jq (Mac) or apt-get install jq (Linux)

Get the agent ID dynamically:

AGENT_ID=$(curl -s http://localhost:2972/a2a/agents | jq -r '.[0].agent_id')
echo "Using agent ID: $AGENT_ID"

Get an agent's card:

curl http://localhost:2972/a2a/agent/$AGENT_ID/.well-known/agent.json

# {"name": "Bedrock_Customer_Support_Agent", "description": "Customer support agent powered by AWS Bedrock AgentCore", "capabilities": {...}}

Invoke an agent via A2A:

curl -X POST http://localhost:2972/a2a/agent/$AGENT_ID/jsonrpc \
  -H "Content-Type: application/json" \
  -d '{"method": "query", "params": {"query": "Hello, I need help with my order"}, "id": 1}'

# Output: {"result": "Hello! I'd be happy to help you with your order..."}

Direct AgentCore Access (Non-A2A)

For debugging or direct integration, you can also call AgentCore agents directly without the A2A protocol.

List the Agentcore agents first:

curl http://localhost:2972/agentcore/agents

# [{"agentRuntimeId": "Bedrock_Customer_Support_Agent-XLA7bpGvk5", "agentRuntimeName": "Bedrock_Customer_Support_Agent", "status": "READY", ...}]

Get the agent runtime ID for direct AgentCore calls:

AGENT_RUNTIME_ID=$(curl -s http://localhost:2972/agentcore/agents | jq -r '.[0].agentRuntimeId')
echo "Using agent runtime ID: $AGENT_RUNTIME_ID"

Then invoke:

curl -X POST http://localhost:2972/agentcore/agents/$AGENT_RUNTIME_ID/invoke \
  -H "Content-Type: application/json" \
  -d '{"prompt": "Hello, I need help with my order"}'

# {"result": {"role": "assistant", "content": [{"text": "Hello! I'd be happy to help..."}]}}

Additional Features

Streaming Responses

The A2A proxy supports streaming responses through both the A2A protocol and direct HTTP endpoints. Agents declare streaming capability in their agent cards:

{
  "capabilities": {
    "streaming": true,
    "pushNotifications": false,
    "stateTransitionHistory": false
  }
}

You can make a streaming call like so:

# Get the agent runtime ID (using jq to extract dynamically)
AGENT_RUNTIME_ID=$(curl -s http://localhost:2972/agentcore/agents | jq -r '.[0].agentRuntimeId')

# Make streaming call
curl -X POST http://localhost:2972/agentcore/agents/$AGENT_RUNTIME_ID/invoke-stream \
  -H "Content-Type: application/json" \
  -H "Accept: text/event-stream" \
  -d '{"prompt": "Tell me a very long and detailed story about Agent-to-Agent (A2A) protocol, including its history, how it works, its benefits, and real-world applications. Please make it comprehensive and engaging."}'

# Output (streaming in real-time):
# data: {"text": "Once"}
# data: {"text": " upon"}
# data: {"text": " a"}
# data: {"text": " time"}
# data: {"text": " in"}
# data: {"text": " the"}
# data: {"text": " world"}
# data: {"text": " of"}
# data: {"text": " distributed"}
# data: {"text": " systems"}
# data: {"text": "..."}
# data: [DONE]

A2A Streaming Implementation: The A2A protocol automatically handles streaming when supported by the underlying AgentCore runtime:

  1. AgentCore Streaming: Modify HTTP client to handle streaming responses

    # Future implementation example
    async def invoke_agent_stream(self, agent_id: str, prompt: str):
        async for chunk in self.stream_invoke(agent_id, prompt):
            yield chunk
    
  2. A2A Stream Handling: Send partial responses via event queue

    # Future AgentCoreExecutor enhancement
    async for chunk in self.http_client.invoke_agent_stream(agent_id, prompt):
        partial_message = Message(
            messageId=str(uuid.uuid4()),
            contextId=context.message.contextId,
            taskId=context.task_id,
            role=Role.agent,
            parts=[Part(root=TextPart(kind="text", text=chunk))],
        )
        await event_queue.enqueue_event(partial_message)
    
  3. Client Usage: A2A clients would receive multiple message events

    # Streaming responses appear as multiple JSON-RPC notifications
    {"result": "Hello"}
    {"result": " there"}
    {"result": "! How"}
    {"result": " can I help?"}
    

Note: Streaming requires AgentCore runtime support for streaming invocations, which may depend on the underlying model and AWS Bedrock configuration.

How It Works

Uses direct HTTPS calls to AgentCore (boto3 SDK not available yet). Discovers agents via bedrock-agentcore-control client and exposes them through standard A2A protocol endpoints. Supports both explicit credentials and default AWS credential chain.

Demo Setup (Complete Infrastructure + Agents)

If you want to try the complete demo with managed infrastructure and agents:

# Set up demo infrastructure (IAM roles, ECR, CloudWatch, etc.)
make install-demo-infrastructure

# Deploy demo agents using the infrastructure
make install-demo-agents

# Clean up everything when done
make uninstall-demo-infrastructure

The demo infrastructure includes:

  • IAM execution role for AgentCore agents
  • ECR repository for container images
  • User policies for agent invocation
  • CloudWatch log groups with retention
  • Bedrock model logging configuration

Configure resources by editing ./demo/infrastructure/terraform.tfvars. Note these resources incur AWS costs.

Custom Infrastructure Setup

If you have your own AWS infrastructure and want to deploy agents to it:

  1. Set environment variables:

    export AWS_ACCESS_KEY_ID=your_key
    export AWS_SECRET_ACCESS_KEY=your_secret
    export AWS_REGION=us-east-1
    export IAM_ROLE_ARN=arn:aws:iam::123456789012:role/YourAgentRole
    export ECR_REPOSITORY_URL=123456789012.dkr.ecr.us-east-1.amazonaws.com/your-repo
    
  2. Deploy specific agents:

    cd demo/agents/customer-support-agents
    make install    # deploy agent
    make uninstall  # remove agent
    

This creates a customer support agent with order lookup and knowledge base capabilities.

Permissions

Requires IAM permissions:

  • bedrock-agentcore:ListAgentRuntimes
  • bedrock-agentcore:DescribeAgentRuntime
  • bedrock-agentcore:InvokeAgentRuntime

TODO

  • Extract AgentCoreHTTPClient from AgentCoreExecutor
  • Add unit tests with mocked HTTP responses
  • Add OIDC authentication support
  • Add support for streaming responses

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

aws_bedrock_a2a_proxy-0.1.2.tar.gz (57.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

aws_bedrock_a2a_proxy-0.1.2-py3-none-any.whl (16.0 kB view details)

Uploaded Python 3

File details

Details for the file aws_bedrock_a2a_proxy-0.1.2.tar.gz.

File metadata

  • Download URL: aws_bedrock_a2a_proxy-0.1.2.tar.gz
  • Upload date:
  • Size: 57.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.12.9

File hashes

Hashes for aws_bedrock_a2a_proxy-0.1.2.tar.gz
Algorithm Hash digest
SHA256 6d407dcf181a178a9187aee479878b56b9dd073348a9fa1228c89befce1488f3
MD5 371224e2fae8ac4aae532be0b01ce1e2
BLAKE2b-256 88889a921e990f2af08f2d97c882aebbbd4c6759f28ec43c0a36fe48dfcc32ca

See more details on using hashes here.

File details

Details for the file aws_bedrock_a2a_proxy-0.1.2-py3-none-any.whl.

File metadata

File hashes

Hashes for aws_bedrock_a2a_proxy-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 378212fd9e7a66cfbf08c7a96a786124577392293a3d408bdd4b52d0ef83d679
MD5 33820a26cedf58510f34ff6020048396
BLAKE2b-256 85ceffd4070979d0f61412b174433e05c65b8f957bef888f2693919d678ff582

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page