AWS 机器学习博客详解用 AWS Agent Registry 实现工具运行时发现
Discover tools at runtime with AWS Agent Registry
AWS Machine Learning Blog 发布教程,讲解 AWS Agent Registry(已正式可用)如何让智能体在运行时通过混合语义和关键词搜索发现 MCP 服务器、A2A 智能体和技能,替代硬编码工具接入。
基于 AWS Agent Registry 的运行时发现机制有助于解决智能体演示可能掩盖的一个问题。硬编码的工具在数量少时运行良好,到几十个时开始退化,超过这个规模就变得难以管理。企业系统对外暴露数百个用于定价、支持、订单、库存和客户数据的内部 API。在这些系统中,模型用于区分工具名称的 token 可能比用于推理用户请求的还多。每新增一项功能都需要修改编排器的代码、重新部署,并在那些本希望按自己节奏发布的团队之间进行协调发布。
这种模式可能出现在企业级软件即服务(SaaS)项目中,团队会向智能体消费者暴露大型内部 API 面。随着目录不断扩大,构建时的接线可能成为瓶颈。一种方法是改变编排器访问工具的方式:不再把每个工具编译进智能体,而是让智能体在运行时发现相关工具。
AWS Agent Registry 是一项用于编目和发现 Model Context Protocol(MCP)服务器、智能体及智能体技能的托管服务。发布者注册特定于协议的描述符和可搜索的描述。在运行时,编排器可以搜索已获批准、可被发现的记录,并使用返回的端点和描述符内容构建客户端。注册表搜索结果不会返回该能力的调用凭证或身份验证方案。
本文将通过重构后的 Python 示例演示 Discover(发现)→ Instantiate(实例化)→ Execute(执行)的循环。该代码通过 Amazon Bedrock AgentCore Gateway(Amazon Bedrock AgentCore 的一项功能)部署一个订单管理 MCP 服务器,在 AgentCore runtime 上部署两个智能体间(A2A)智能体,以及一个注册表和一个编排器。示例目录包含部署脚本、编排器、辅助模块和清理脚本。
解决方案概览:发现、实例化、执行
本示例中的编排器智能体不具备关于工具或智能体的任何内置知识。
图 1:没有 AWS Agent Registry 时(左),端点被硬编码,新增一个智能体意味着代码更改加重新部署。使用 AWS Agent Registry 时(右),编排器通过语义搜索发现能力,新集成在注册并获得批准后即可使用。
发现
编排器向 AWS Agent Registry 数据平面发送自然语言查询。搜索响应包含记录标识、名称、描述、记录类型、状态、版本以及协议描述符(例如 MCP 服务器元数据或 A2A 智能体卡片),但不包含调用凭证。应用程序必须通过单独的可信配置路径获取并应用相应的凭证。
实例化
对于每条返回的记录,编排器根据描述符类型构建一个客户端。在本示例中,注册的 MCP 服务器代表最初作为目标添加到 Amazon Bedrock AgentCore Gateway 的工具,因此 MCP 描述符指向该 Gateway 端点。编排器单独获取 Cognito OAuth 访问令牌,并在创建 MCPClient 时使用它。A2A 记录包含一张智能体卡片,其 URL 标识一个 AgentCore runtime 端点。封装器通过 boto3 数据平面客户端调用该运行时,该客户端使用调用者的 AWS 凭证对请求进行签名。注册表发现只提供连接元数据,而不提供身份验证材料。
执行
仅使用动态发现的工具构建一个临时内部智能体。大语言模型(LLM)为该请求挑选合适的工具,并将结果综合后返回给用户。当这一轮结束后,内部智能体及其客户端会被拆除。下一个请求将获得全新的搜索和全新的工具集。
图 2:端到端架构。Amazon Bedrock AgentCore 运行时上的单个编排器查询 AWS Agent Registry。匹配的 MCP 服务器通过 Amazon Bedrock AgentCore Gateway 调用,匹配的 A2A 智能体在 Amazon Bedrock AgentCore 运行时上调用
示例中使用的参考架构包括 AWS Agent Registry、Amazon Bedrock AgentCore Gateway、Amazon Bedrock AgentCore runtime、Amazon Bedrock、Amazon Cognito、AWS Lambda 和 AWS Secrets Manager。
- AWS Agent Registry 提供由编排器查询的受治理、可搜索的目录。只有完成所配置审批工作流的记录才能通过可发现的数据平面访问。
- Amazon Bedrock AgentCore Gateway 将订单管理 Lambda 工具作为 MCP 服务器公开。该示例为入站 Gateway 调用配置了 Cognito JWT 授权,并使用 Gateway 的 AWS Identity and Access Management(IAM)角色来调用 Lambda 目标。
- Amazon Bedrock AgentCore runtime 承载编排器以及定价和客户支持 A2A 智能体。运行时调用使用 IAM 授权的 Boto3 调用。
- Amazon Bedrock 提供编排器和 A2A 智能体所使用的基础模型(FM)。该示例目前通过跨区域模型 ID 配置 Anthropic Claude Sonnet 模型。参见 Amazon Bedrock 中各 AWS 区域支持的模型。
三个演示场景以不同的能力组合来演练发现循环。第一个是仅 MCP 的调用(订单状态)。第二个是链式 MCP + A2A(定价和折扣)。第三个针对模糊的用户意图测试纯语义匹配:退货和退款,这些词并不出现在匹配到的 A2A 智能体的名称中。
技术实现
链接的运行时发现示例会部署依赖项、创建并填充 Registry、验证发现、部署编排器并运行三个演示。orchestrator_agent.py 包含每次请求的发现循环。utils.py 解析 Registry 描述符并创建 MCP 和 A2A 客户端。cleanup.py 用于删除资源。
1. 注册模型
一条 Registry 记录包含可搜索的描述以及特定于协议的描述符。该示例使用 Agent Registry 控制平面客户端执行 Registry 和记录生命周期操作,并使用 Agent Registry 数据平面客户端进行运行时发现。
创建具有手动审批和 IAM 授权的 Registry。
registry_client = session.client("agent-registry-control")
dp_client = session.client("agent-registry")
reg = registry_client.create_registry(
name="OrderManagementRegistry",
description=(
"Registry for Order Management & Customer Service — "
"agent discovers tools and agents via semantic search"
),
approvalConfiguration={"autoApprovalRules": []},
)
REGISTRY_ARN = reg["registryArn"]
REGISTRY_ID = REGISTRY_ARN.split("/")[-1]创建记录时 recordType 字段是必需的。在此示例中,MCP 服务器使用 recordType="MCP",而基于 A2A 的智能体使用 recordType="AGENT"。协议元数据存储在 descriptors 对象中的 mcpServer 或 a2aAgentCard 之下。MCP 描述符包含服务器元数据和工具定义。A2A 描述符包含智能体卡片。描述符包含连接元数据,但不包含调用者在调用该能力时必须出示的凭证。
为 MCP 和 A2A 记录构建当前的公共 SDK 描述符形态。
# MCP descriptor
mcp_descriptors = {
"mcpServer": {
"data": json.dumps(server_metadata),
"dataSchemaVersion": "2025-12-11",
"additionalData": {
"tools": {
"data": json.dumps({"tools": tool_schemas}),
"dataSchemaVersion": "2025-06-18",
}
},
}
}
# A2A descriptor
a2a_descriptors = {
"a2aAgentCard": {
"data": json.dumps(agent_card),
"dataSchemaVersion": "0.3",
}
}用面向用户的语言编写描述,使该能力与相邻记录区分开来。描述内容提供协议特定的服务器、工具或智能体卡片数据。搜索质量应使用有代表性的查询进行评估。本文不假设目录增长会自动提升排名。
使用当前的控制平面形态创建 Registry 记录。
descriptors = (
mcp_descriptors
if cfg["protocol"] == "MCP"
else a2a_descriptors
)
response = registry_client.create_registry_record(
registryId=REGISTRY_ID,
name=name,
description=cfg["description"],
recordType=cfg["protocol"],
descriptors=descriptors,
recordVersion="1.0",
)
record_id = response["recordId"]2. 审批工作流
当 autoApproval 设置为 false 时,新记录必须从 DRAFT 转移到 PENDING_APPROVAL,再到 APPROVED。提交和状态更新操作是 经 IAM 授权的,允许将发布者和审批者的权限分离。只有已批准的记录才会由可发现的 Registry 数据平面返回。
两步审批流转。
record = registry_client.get_registry_record(
registryId=REGISTRY_ID,
recordId=record_id,
)
if record["status"] == "DRAFT":
registry_client.submit_registry_record_for_approval(
registryId=REGISTRY_ID,
recordId=record_id,
)
registry_client.update_registry_record_status(
registryId=REGISTRY_ID,
recordId=record_id,
status="APPROVED",
statusReason="Approved",
)3. 发现层
数据平面客户端支持对可发现记录进行关键词与语义混合搜索。最新的方法名称是 search_discoverable_registry_records。结果会公开规范化的记录字段和可发现的描述符,但不会公开该能力的调用凭据。
跨协议搜索已批准、可发现的记录。
response = dp_client.search_discoverable_registry_records(
registryIds=[REGISTRY_ARN],
searchQuery=query,
maxResults=3,
)
records = response.get("registryRecords", [])在示例场景中,一次退货与退款查询会检索到 Customer Support Agent,因为它的描述捕捉到了这一意图。请将此视为演示结果,而不是“目录更大排名就会提升”的一般性论断。
4. 编排器
编排器是一个部署到 Amazon Bedrock AgentCore runtime 的 Strands 智能体。它暴露 discover_and_execute,该工具会搜索 Registry、解析每个返回的描述符、创建相应的 MCP 或 A2A 客户端,并仅用这些发现的能力构建一个请求作用域的内部智能体。
图 3:编排器每次请求的流程。外部智能体将用户请求转换为 Registry 搜索。内部智能体由搜索结果组装而成,并在该轮结束时销毁
discover_and_execute 的核心可以放进一个代码块中:
编排器的发现/实例化/执行循环。
@tool
def discover_and_execute(request: str) -> str:
records = dp_client.search_discoverable_registry_records(
registryIds=[REGISTRY_ARN],
searchQuery=request,
maxResults=5,
).get("registryRecords", [])
# Registry returns descriptors, not invocation credentials.
oauth_token = fetch_oauth_token_from_config()
mcp_clients, a2a_tools = [], []
for record in records:
metadata = parse_server_metadata(record)
if metadata["protocol"] == "MCP":
mcp_clients.append(
create_mcp_client_from_metadata(metadata, oauth_token)
)
elif metadata["protocol"] == "A2A":
a2a_tools.append(
create_a2a_tool_from_metadata(metadata, session, REGION)
)
return run_request_scoped_agent(request, mcp_clients, a2a_tools)
model = BedrockModel(model_id=MODEL_ID, region_name=REGION)
started_clients = []
try:
mcp_tools = []
for c in mcp_clients:
c.start()
started_clients.append(c)
mcp_tools.extend(c.list_tools_sync())
##agent compiled in realtime within agent
sub_agent = Agent(
model=model,
tools=mcp_tools + a2a_tools,
system_prompt=(
"You are an Order Management & Customer Service assistant. "
"Use the RIGHT tool for each request:\\n"
"- Order lookups, status, cancellations, address changes: use MCP tools\\n"
"- Pricing, discounts, promo codes: use the pricing_agent tool\\n"
"- Returns, refunds, complaints, escalations: use the customer_support_agent tool\\n"
"Always use the most specific tool for the task."
),
)
return str(sub_agent(request))
finally:
for c in started_clients:
try:
c.stop()
except Exception:
pass 该示例并行发出多个搜索查询以提高其订单管理领域的召回率,对记录去重,并在请求结束后销毁 MCP 客户端。这种并行展开是示例特有的编排选择,并非 Registry 的要求。身份验证仍在发现流程之外:Gateway OAuth 令牌从 Cognito 配置和 Secrets Manager 获取,而 A2A runtime 调用则通过 boto3 会话进行签名。
5. 运行三个演示
每个演示都演练了发现循环的不同形态。
演示 1:订单状态(仅 MCP)
一个解析为单次 MCP 工具调用的请求。
result = invoke_orchestrator(
"What is the current status and tracking info for order 123?",
agentcore_client, orchestrator_arn,
)Registry 返回订单管理 MCP 服务器。编排器通过 Gateway 调用 get_order_status,LLM 合成出人类可读的响应,然后内部智能体终止。这一轮不涉及 A2A。
演示 2:定价与折扣(MCP + A2A)
一个解析为多协议链的请求。
result = invoke_orchestrator(
"Order 123 has 2x Widget Pro at $99.98. What discount tiers or "
"promo codes can reduce the price?",
agentcore_client, orchestrator_arn,
)Registry 返回订单管理 MCP 服务器和定价 A2A 智能体:两种协议,一条自然语言查询。LLM 调用 get_order_status 获取订单明细,然后在 runtime 上调用定价智能体进行折扣分析,最后合成一条建议。
演示 3:退货与退款(语义匹配)
一个其意图没有从字面上出现在任何工具名称中的请求。
result = invoke_orchestrator(
"I want to return order 789 (Premium Headphones, delivered "
"March 10). Am I eligible for a return and what is the refund "
"amount?",
agentcore_client, orchestrator_arn,
)该演示展示了语义发现的价值。“return refund(退款)”这个短语并未出现在客户支持智能体的注册名称中。混合搜索之所以将其排在高位,是因为该智能体的描述捕捉到了意图。如果没有 Registry,编排器将需要硬编码的知识来确定哪个智能体处理退货。
6. 可观测性
在适当的情况下,使用 Amazon Bedrock AgentCore Observability 和 Amazon CloudWatch 对发现和调用路径进行监测。有用的信号包括 Registry 搜索的成功与失败、所选记录标识符、客户端构造错误、下游调用结果、端到端追踪关联以及应用程序错误。该示例授予了 Amazon CloudWatch Logs 权限,但并未创建自定义指标或仪表板。生产团队应为其运营模式定义所需的追踪、日志和警报。生产部署还应将 Amazon Bedrock Guardrails 作为智能体响应的标准控制手段。
受治理的运行时发现能为团队带来什么
发现循环就位后,之前与编排器发布耦合的若干能力便可以独立开来。
- 解耦发布。团队可以部署并注册自己的 MCP 服务器、智能体和技能。审批策略决定了已发布记录何时对消费者可用。
- 新增已批准记录无需更改编排器代码。在此模式下,添加一个兼容且已获批准的 Registry 记录,无需在编排器中添加特定于工具的导入或端点。不过,协议、身份验证设置或编排策略的变更仍可能需要更新代码或配置。
- 受治理的发现。通过手动审批,只有经过审核和批准的记录才会变得可发现。IAM 权限可以将记录发布者与审批者分离开来。
- 身份验证分离。Registry 授权可以使用 IAM 或自定义 JWT。能力调用的身份验证是独立的:该示例对 Gateway 使用 Cognito OAuth,对 AgentCore 运行时使用 Boto3/IAM 签名。搜索结果不会返回这些凭据。
- 目录搜索而非提示词堆砌。借助 Registry 的混合搜索,编排器检索的是一小部分候选集,而不是将整个目录放入模型上下文中。搜索质量取决于描述、描述符质量、查询设计和评估。
何时不适合使用运行时发现
并非所有工作负载都需要运行时发现。以下两种模式仍可能更适合显式的构建时连接:
- 小型且稳定的目录。如果完整的能力集合很小且很少变动,显式的构建时连接可能更简单,并可避免额外的发现请求。
- 固定流水线。当相同的能力始终以固定顺序运行时,将其实现为确定性流程更为直接,并能让追踪保持聚焦。
结论
在运行时从 Registry 发现资产,可降低编排器对固定目录的依赖。借助 AWS Agent Registry,编排器可以通过语义与关键词混合搜索来检索已批准的能力,解析 MCP 或 A2A 描述符,并实例化请求作用域的客户端。治理决定了哪些内容可被发现。对于 Registry 和每个被调用的能力而言,身份验证仍是一个需要显式处理的事项。
AWS Agent Registry 已正式发布(GA),其能力远不止这个单账户示例所示:
- 组织范围的发现与跨账户共享可以通过受支持的 AWS Organizations 及共享机制,跨账户边界公开受治理的记录。
- 自动能力同步可以从一个 URL 填充受支持的描述符。该同步请求上的凭据提供程序配置用于获取描述符内容,它不会作为调用身份验证返回给运行时使用方。
- 审批工作流可以使用 Registry 状态 API 和 IAM 权限,将 CI 检查、安全审查或人工审批接入
DRAFT→PENDING_APPROVAL→APPROVED生命周期。 - 标签、AWS CloudFormation 支持以及基础设施即代码模式可以让 Registry 的部署和治理可重复。评估时应针对组织自身的目录验证搜索相关性和调用行为。
运行运行时发现示例,然后注册一个你自己的兼容 MCP 服务器或智能体。确认其描述符、审批状态、身份验证路径和搜索行为符合你的生产要求。
了解更多
- AWS Agent Registry 正式发布公告
- AWS Agent Registry 文档
- Amazon Bedrock AgentCore 控制台(Registry)
- AWS Agent Registry 正式发布技术博客文章
关于作者
来源: AWS Machine Learning Blog · aws.amazon.com


