Python Agent から A2A Agent への接続
connection ジェネレーターは、Python Agent をリモートの A2A エージェント(TypeScript または Python)に接続し、エージェントが別のエージェントにツールとして委任できるようにします。
このジェネレーターは、AWS へのデプロイ時(Bedrock AgentCore 経由)とローカル実行時の両方で、エージェントがリモート A2A エージェントを検出して呼び出すために必要なすべての配線を設定します。
このジェネレーターを使用する前に、以下を確認してください:
- Python Agent コンポーネント(Strands または LangChain)を持つ Python プロジェクト
--protocol=A2Aと--auth=IAMで生成された Agent コンポーネントを持つプロジェクト(ts#agentまたはpy#agentのいずれか)- 両方のコンポーネントが
infra: agentcoreで作成されていること
ジェネレーターの実行
Section titled “ジェネレーターの実行”- インストール Nx Console VSCode Plugin まだインストールしていない場合
- VSCodeでNxコンソールを開く
- クリック
Generate (UI)"Common Nx Commands"セクションで - 検索
@aws/nx-plugin - connection - 必須パラメータを入力
- クリック
Generate
pnpm nx g @aws/nx-plugin:connectionyarn nx g @aws/nx-plugin:connectionnpx nx g @aws/nx-plugin:connectionbunx nx g @aws/nx-plugin:connectionソースとしてホストエージェントプロジェクトを、ターゲットとして A2A エージェントプロジェクトを選択します。プロジェクトに複数のコンポーネントが含まれている場合は、sourceComponent と targetComponent オプションを指定して明確にしてください。
| パラメータ | 型 | デフォルト | 説明 |
|---|---|---|---|
| sourceProject 必須 | string | - | ソース プロジェクト |
| targetProject 必須 | string | - | 接続先のターゲット プロジェクト |
| sourceComponent | string | - | 接続元のソース コンポーネント (コンポーネント名、ソース プロジェクト ルートからの相対パス、またはジェネレーター ID)。プロジェクトをソースとして明示的に選択するには '.' を使用します。 |
| targetComponent | string | - | 接続先のターゲット コンポーネント (コンポーネント名、ターゲット プロジェクト ルートからの相対パス、またはジェネレーター ID)。プロジェクトをターゲットとして明示的に選択するには '.' を使用します。 |
| preferInstallDependencies | boolean | true | ジェネレーター実行後に依存関係のインストールを優先するかどうか。複数のジェネレーターをバッチ処理する際にインストールを延期する場合はfalseに設定します(後続のジェネレーターがNxプロジェクトグラフを計算できるよう、必要に応じてインストールは実行されます)。最後に一度だけインストールします。 |
ジェネレーターの出力
Section titled “ジェネレーターの出力”ジェネレーターは、packages/common/agent_connection/ に共有の agent_connection Python プロジェクトを作成します(まだ存在しない場合)。接続ごとのクライアントモジュールがこの共有プロジェクトに生成されます:
Directorypackages/common/agent_connection
Directory<scope>_agent_connection
- __init__.py 接続ごとのクライアントを再エクスポート
Directorycore
- agentcore_endpoints.py フレームワークに依存しない ARN/URL 解決
- agentcore_a2a_client_config.py フレームワークに依存しない A2A クライアント設定(署名済み
ClientConfig) - agentcore_a2a_client_<framework>.py エージェントのフレームワーク用の設定をラップする A2A クライアント
Directoryauth/ フレームワークに依存しない SigV4 / セッション転送
httpx.Auth- …
Directoryapp
- <target_agent_name>_client_<framework>.py 各 A2A エージェント用の接続ごとの A2A クライアント
クライアントのサフィックスはエージェントのフレームワーク(_strands または _langchain)に一致します。両方とも同じフレームワークに依存しない署名済み ClientConfig をラップします: Strands クライアントは Strands の A2AAgent をラップし、LangChain クライアントは a2a SDK を直接駆動するため、LangChain エージェントは Strands の依存関係を持ちません。
さらに、ジェネレーターは以下を行います:
- エージェントの
agent.pyを変換して、リモート A2A エージェントを@toolを使用してツールとして登録 - エージェントプロジェクトのワークスペース依存関係として
agent_connectionプロジェクトを追加 - エージェントの
serve-localターゲットを更新して、ターゲットエージェントのserve-localターゲットに依存するようにする
接続された A2A エージェントの使用
Section titled “接続された A2A エージェントの使用”ジェネレーターは、エージェントの agent.py を変換して、リモート A2A エージェントをツールとしてラップします。リモートエージェントは @tool でデコレートされたデリゲートとして登録されます — デコレーターのインポートとエージェントのコンストラクターはフレームワークによって異なります:
from contextlib import contextmanagerfrom strands import Agent, tool
from my_scope_agent_connection import RemoteAgentClientStrands
@contextmanagerdef get_agent(): remote_agent = RemoteAgentClientStrands.create()
@tool def ask_remote_agent(prompt: str) -> str: """Delegate a question to the remote RemoteAgent A2A agent and return its reply.""" return str(remote_agent(prompt))
yield Agent( system_prompt="...", tools=[ask_remote_agent], )from langchain.agents import create_agentfrom langchain_aws import ChatBedrockConversefrom langchain_core.tools import tool
from my_scope_agent_connection import RemoteAgentClientLangChain
def get_agent(): remote_agent = RemoteAgentClientLangChain.create()
@tool def ask_remote_agent(prompt: str) -> str: """Delegate a question to the remote RemoteAgent A2A agent and return its reply.""" return str(remote_agent(prompt))
return create_agent( model=ChatBedrockConverse(model=MODEL_ID, region_name=REGION), system_prompt="...", tools=[ask_remote_agent], )両方のクライアントは直接呼び出し可能で、リモートエージェントの応答を返します。また、AWS にデプロイされた際に SigV4 でリクエストに署名し、LOCAL_DEV=true の場合はプレーンな http://localhost:<port>/ エンドポイントを使用する httpx.AsyncClient をラップします。Strands クライアントは Strands の A2AAgent をラップし、LangChain クライアントは a2a SDK を直接駆動します。
AgentCore セッション ID は、フレームワークに関係なく X-Amzn-Bedrock-AgentCore-Runtime-Session-Id ヘッダーを介してリモートエージェントに自動的に伝播されます: エージェントサーバーは受信リクエストのセッションを非同期コンテキストにバインドし、接続クライアントの署名済み httpx.Auth がすべての送信呼び出しにそれをスタンプします — これにより Bedrock AgentCore Observability の一貫性が確保されます。
インフラストラクチャ
Section titled “インフラストラクチャ”接続ジェネレーターを実行した後、ホストエージェントがリモート A2A エージェントを呼び出す権限を付与する必要があります。
const remoteAgent = new RemoteAgent(this, 'RemoteAgent');const myAgent = new MyAgent(this, 'MyAgent');
// Grant the host agent permission to invoke the remote A2A agentremoteAgent.grantInvokeAccess(myAgent);A2A エージェントの grantInvokeAccess は、bedrock-agentcore:InvokeAgentRuntime と bedrock-agentcore:GetAgentCard の両方を設定します。A2A クライアントは、エージェントカードを取得してメッセージを送信するために両方が必要です。
リモートエージェントの AgentCore ランタイム ARN は、生成された CDK コンストラクトによって Runtime Configuration の agentcore 名前空間に自動的に登録されるため、ホストエージェントは実行時にそれを検出できます。
module "remote_agent" { source = "../../common/terraform/src/app/agents/remote-agent"
appconfig_application_id = module.runtime_config_appconfig.application_id appconfig_application_arn = module.runtime_config_appconfig.application_arn}
module "my_agent" { source = "../../common/terraform/src/app/agents/my-agent"
appconfig_application_id = module.runtime_config_appconfig.application_id appconfig_application_arn = module.runtime_config_appconfig.application_arn}
# Grant the host agent permission to invoke the remote A2A agentresource "aws_iam_policy" "agent_invoke_a2a" { name = "AgentInvokeA2aPolicy" policy = jsonencode({ Version = "2012-10-17" Statement = [{ Effect = "Allow" Action = [ "bedrock-agentcore:InvokeAgentRuntime", "bedrock-agentcore:GetAgentCard", ] Resource = module.remote_agent.agent_core_runtime_arn }] })}
resource "aws_iam_role_policy_attachment" "agent_invoke_a2a" { role = module.my_agent.agent_core_runtime_role_arn policy_arn = aws_iam_policy.agent_invoke_a2a.arn}リモートエージェントの AgentCore ランタイム ARN は、生成された Terraform モジュールによって Runtime Configuration の agentcore 名前空間に自動的に登録されるため、ホストエージェントは実行時にそれを検出できます。
ローカル開発
Section titled “ローカル開発”ジェネレーターは、ホストエージェントの serve-local ターゲットを以下のように構成します:
- 接続された A2A エージェントを自動的に起動
SERVE_LOCAL=trueを設定して、生成されたクライアントが AgentCore の代わりにhttp://localhost:<port>/に直接接続するようにする
エージェントをローカルで実行するには:
pnpm nx <agent-name>-dev <project-name>yarn nx <agent-name>-dev <project-name>npx nx <agent-name>-dev <project-name>bunx nx <agent-name>-dev <project-name>これにより、ホストエージェントとすべての接続された A2A エージェントが起動し、ホストエージェントは割り当てられたローカルポートでプレーン HTTP を介してリモートエージェントを呼び出します。