让 Agent 直接调外部 API 是企业 Agentic 最贵的架构错误——5 层分层 + 25 个 API 契约清单|Agentic AI 落地方法论(九)

《Agentic AI 落地方法论》系列第九篇。 前八篇拆「方案能不能上线 + 上线后怎么不放养 + 北极星指标 + 脑和手 + 怎么测 + 意图分级」——L0-L3 定级、L2 vs L3 5 决策、Critic fail-closed、上线即放养、接住率 vs 解决率、脑和手、双轨测试。这一篇换一个方向——为什么 90% 的企业 Agentic 项目在「接外部 API」这一层就把架构建错了,和怎么把这条线划清楚。English version: Five-Layer Architecture for Agentic Enterprise APIs.
「我们接了 25 个 API」——架构评审会上最贵的伪信号
某次架构评审会,乙方 PPT 翻到第 23 页:
「已对接外部系统 6 个:订单 OMS、工单平台、物流提供方、仓储 WMS、客服 IM 渠道、知识库中心;总计 25 个 API 接口;Agent 端 Tool 数 7 个;端到端覆盖售后退款、物流跟踪、工单创建等 12 个核心场景。」
老板点头。然后随口问了三件事:
- 「换 OMS 供应商怎么办?」乙方答:「LLM Tool 重写一遍。」
- 「QA 在 OMS 接口没就绪之前怎么联调?」乙方答:「等供应商接口出来再说。」
- 「下个月合规审计要看每一次退款的链路日志,能不能给?」乙方答:「我们后面加点日志吧。」
那一刻整个项目组都意识到一件事:25 个 API 全接通了不代表架构对了。它只证明「LLM 当前能调到外部系统」,没证明这套系统换供应商时不用重写、缺接口时能联调、写操作有审计链路、出事故能回滚到具体 API——这四件事才是企业级 Agentic 架构的真正基本面。
这一年我跟的所有客服 Agent 项目里,最贵的架构错误都不在算法、不在模型选型、不在向量库选哪家——是在这一条:让 LLM Tool 直接调外部 API。看起来最短路径、上线最快、PPT 最好看,但 3 个月后第一次换供应商、第一次合规审计、第一次出生产事故时,整个 Tool 层和外部系统都要拆掉重写。
这一篇写给正在带企业 Agentic 落地的架构负责人、老板、项目需求方——API 集成是落地里最容易被「我们接了 25 个 API」糊弄过去、但出问题代价最大的一环。拆四件事:(1)「Agent 直连 API」这个伪架构的三个真实代价、(2)5 层架构(Adapter / Service ABC / Tool / Workflow / Critic)每一层的职责边界、(3)6 大外部系统 25 个 API 的接入矩阵——直接当下次架构评审的拍板清单、(4)5 件本周要推动的架构决策。
「Agent 直接调外部 API」——三个企业级的真实代价
先把结论摆桌面上:让 LLM Tool 直接调外部接口看起来路径短,但本质是把企业级的「契约 / 抽象 / 审计」三层都跳过了。代价不在 demo 阶段显现,3 个月后必出。
代价一:换供应商等于重写。 OMS 字段命名规范换一套(驼峰 → 下划线、新增必填字段),工单系统主版本升级(v4.x → v5.x),物流提供方从 A 切到 B——任何一个企业系统的对接方变化,Tool 层全部要改。我见过的项目里有一个,因为 OMS 中台升级一次接口规范,整套 Agent 的 7 个 Tool 都要回归测试,4 个研发同学加班 3 周。本质是 LLM Tool 和外部系统耦合在了一起,LLM 看见的「接口名」就是供应商的「接口名」。
代价二:缺接口时整个项目卡住。 公域电商平台(抖音 / 天猫 / 京东)的真实 API 还在等商务确认;工单系统的字段定义还在等业务方;仓储 WMS 的认证方式还没定下来——如果 Tool 直接调这些接口,那这些接口不出来项目就卡住。我见过的项目里 80% 的工时浪费都耗在这种「等接口」的死循环里。本质是没有 Mock 契约层,dev 和 QA 拿不到任何东西做联调。
代价三:合规审计的最后一公里跑不通。 写操作(退款 / 取消订单 / 撤工单)出了事故,合规和财务要回看:哪一条对话触发了 Tool ?参数怎么填的?谁拍板的(LLM?Workflow?Critic?Rules?业务签字阈值?)?这种「调用链 + 决策依据 + 业务签字」的审计闭环,LLM 直连 API 的架构里根本没有。事故发生时只能看到「LLM 输出了 approve」,没有任何中间层能告诉你这个 approve 经过了什么校验。
三个代价拼起来就是:「Agent 直连 API」用 demo 速度换走了企业级架构最重要的三种能力——可替换的供应商、可联调的契约、可审计的链路。没有这三种能力,企业级 Agentic 项目就只是个 PPT。
5 层架构:Adapter → Service ABC → Tool → Workflow → Critic
先把结论摆桌面上:企业级 Agentic 系统连接外部 API 这一段,必须分 5 层。每一层只解决一件事,每一层的契约都不互相穿透。少任何一层都会在 3 个月后翻车。
| 层 | 解决的问题 | 关键产出物 | Owner |
|---|---|---|---|
| L1 Adapter(适配器) | 把外部 SaaS 的字段、协议、鉴权、错误码翻译成内部协议 | 每个外部系统一个 Adapter(OAuth Token 缓存、字段大小驼峰映射、非成功业务码抛 XxxBizError、HTTP 重试) | 后端研发 |
| L2 Service ABC(服务抽象) | 让业务层不知道用的是哪个 provider | OrderClient / TicketClient / LogisticsClient 抽象基类 + Mock 实现 + Real 实现,环境变量 SERVICES_BACKEND=mock|real 切换 | 后端研发 + 业务签字 |
| L3 Tool(工具) | 给 LLM 看的接口契约——名字、参数 schema、read_only 标志 | 7-12 个 Tool,每个有 description / parameters JSON Schema / read_only 标志;ToolRegistry 统一注册 | 后端研发 + AI 运维 |
| L4 Workflow(流程编排) | 写操作的多步编排 + 安全限制 | check_params → query → validate → critic_check → execute → notify;max_steps 安全限制;human_review 兜底 | 后端研发 + 业务签字 |
| L5 Critic + Rules(写操作兜底) | 在「LLM 决定」和「真的改外部系统」之间加一道闸 | LLM Critic(语义层)+ Rules(硬规则层:金额阈值、订单 7 天窗口、24h 重复退款),fail-closed | 业务方 + AI 运维 + 法务签字 |
每一层的边界,落地负责人必须能在白板上画出来——画不出来就是架构没分清:
- LLM 看不见 Adapter:Adapter 在最底层,LLM 永远不会调
order_gateway.list_orders(),它只会调 Tool。Tool 调 Service ABC,Service ABC 才调 Adapter。 - 业务层看不见 provider:业务 Workflow 调的是
order_client.get_by_user(user_id),不知道这个order_client是MockOrderClient还是RealOrderClient,更不知道底下用的是 OMS A 还是 OMS B。 - Tool 暴露给 LLM 的契约不暴露内部结构:Tool 的
description是「查询订单」,不是「调用订单网关的/orders/list端点」。LLM 看不到端点路径、看不到字段映射、看不到鉴权。 - 写操作必经 Critic:任何修改外部状态的 Tool(
cancel_order/create_refund/cancel_ticket),Workflow DSL 里强制要求经过critic_checkStep,绕过就是架构 bug。 - 配置三层分开:服务 / 流程开关在代码 + 环境变量;业务阈值在
thresholds.yaml(业务签字);运维监控阈值在 Dashboard 配置。三层分开,三种人各管各的,互不污染。
这 5 层不是「架构师追求优雅」——是企业级 Agentic 项目能不能熬过供应商替换、合规审计、生产事故的基础免疫力。每一层都能在白板上画出职责边界,团队才有共同语言;少任何一层都会在某个具体场景下让整个项目变成「重写」。
这张图直接搬到下次架构评审会的白板上:架构负责人画不出 5 层职责的,团队就没有共同语言。「换供应商时哪一层动 / 测试时哪一层切 Mock / 合规审计追到哪一层」——三个问题的答案都在这张图里。L1 Adapter 层——把外部系统翻译成内部协议的「翻译官」
先把结论摆桌面上:Adapter 层只做翻译,不做业务判断。每个外部 SaaS 一个 Adapter,越独立越好——这一层是企业级 Agentic 「换供应商无痛」的真正实现位置。
Adapter 应该处理的 6 件事,每一件都对应一个真实踩过的坑:
1. 鉴权抽象——OAuth Client Credentials + Token 缓存 + 并发刷新
订单网关用 OAuth2,Token 30 分钟过期。最朴素的写法是「每次调用前 check token 然后刷新」——这种写法在并发场景下会出灾难:100 个请求同时到 + Token 同时过期 → 100 个并发 /oauth/token 调用 → 网关被打挂。正确做法是 Adapter 内部维护 Token 缓存 + 用 asyncio.Lock 防止并发刷新雪崩 + 过期前 60s 主动续签 + 401 自动清缓存 + 重试一次。这套机制写一次留在 Adapter,Service ABC 以上的所有人不需要知道 Token 这件事。
2. 字段映射——大驼峰 / 小驼峰 / 下划线的「外交」
订单网关返回 code(不同供应商命名各异:bizCode / statusCode / code 都有),内部协议统一成 biz_code;OMS 字段叫 productCode,内部叫 sku_id;工单平台用 requestId,内部用 ticket_id。所有这些命名差异在 Adapter 里被 from_dict / to_dict 方法吃掉。Service ABC 以上拿到的全是内部协议的 dataclass,外部供应商怎么命名根本不知道。
3. 错误码抽象——非成功业务码抛 XxxBizError
订单网关用业务码区分成功/失败(例如 code=0 表示成功,code=1004 表示订单不存在);工单平台用 HTTP 状态码 + 自定义 error_code;物流提供方用 result.success == false。这些异构错误码全部在 Adapter 里翻译成 XxxBizError(code, msg)。Service ABC 以上拿到的全是 Python 异常,统一 try/except 处理。
4. 环境隔离——X-Env 头
测试环境调真实接口要带 X-Env: staging,生产不带。这种隔离标记在 Adapter 内部按环境变量自动注入——业务代码看不到这个 header,不可能因为忘了带而把测试流量打进生产。
5. 重试 + 超时——HTTP 层的硬规则
httpx 配 timeout=10s、connect_timeout=3s,401 重试一次(清 token 后),HTTP 5xx 不重试(向上抛异常给业务层处理)。这套规则在 Adapter 里统一定义,所有调用走同一份配置——出问题的时候不用追查每个 Tool 是不是各自加了 retry。
6. 输入校验——SQL/路径注入的第一道墙
订单号里有 "'; DROP TABLE;--" 怎么办?httpx 自动转义 URL 参数能挡住大部分;Adapter 在调用前做一次最严的 schema 校验(订单号正则、金额 ≥ 0、日期格式),异常输入直接拒绝——不是「Critic 兜底」级别的兜底,是「第一道墙」级别的拒绝。
Adapter 层最反直觉的工程纪律是:它的代码越「无聊」越好——纯翻译、纯重试、纯字段映射,任何带业务判断的逻辑都是错的。退款金额能不能改、订单能不能取消,Adapter 一概不管——这些是 Service 层 + Critic 层 + Rules 层的责任。Adapter 越纯净,换供应商时受影响的代码越少。
Adapter 是企业级 Agentic「换供应商无痛」的实际实现位置。任何带业务判断的代码在 Adapter 层都是错位的——架构负责人 code review 时看到这一层有「if amount > X then reject」这样的逻辑,就该退回去重构到 Critic / Rules 层。L2 Service ABC 层——业务层不知道用的是哪个 Provider
先把结论摆桌面上:Service ABC 是企业级 Agentic 「Mock 联调 / 换供应商 / A/B 切换」的真正抽象点。业务 Workflow 调的是 ABC,不是 Adapter——这一条搞错了,整个项目的可换性就废了。
Service ABC 长什么样?以订单服务为例:
class OrderClient(ABC):
@abstractmethod
async def get_by_user(self, user_id: str) -> list[OrderInfo]: ...
@abstractmethod
async def get_by_id(self, order_id: str) -> OrderInfo | None: ...
@abstractmethod
async def get_active_orders(self) -> list[OrderInfo]: ...
@abstractmethod
async def cancel_order(self, order_id: str) -> CancelResult: ...
@abstractmethod
async def close(self) -> None: ...
然后有两个实现:
MockOrderClient:写一组固定的 mock 订单(ORD-2026-0322-099是 happy path、ORD-2026-0308-042是超时边界、ORD-2026-0311-001是物流追踪场景)RealOrderClient:内部直接调OrderGatewayAdapter,把网关响应翻译成OrderInfodataclass
环境变量 SERVICES_BACKEND=mock|real 控制注入哪个实现。业务 Workflow 一行不用改。
Service ABC 解决的四件事:
1. Mock 优先于 Real——dev / QA 联调不卡接口就绪
公域电商平台接口还在等商务确认?不重要。先用业务方拍板的 schema 写 MockEcommerceClient,QA 就可以基于 Mock 写完所有 E2E 场景用例。等真实接口出来再切 SERVICES_BACKEND=real 跑一次契约一致性测试(Pact 或 schema 对齐)就完事。项目排期不会再被「等接口」拖死——这一条是企业级 Agentic 团队和小作坊的分水岭。
2. 契约一致性测试——保证 Mock 不撒谎
MockOrderClient 实现的所有方法签名 + 返回值结构必须和 RealOrderClient 一致——这件事用 pytest 的 test_contract_services.py 强制校验:Mock 不实现 ABC 的任何 abstract method = 测试挂 = PR 进不去主干。这样保证了「Mock 联调跑通」≠「Real 切上去爆炸」。
3. 换供应商无痛——只改 Adapter,不动 ABC
OMS 中台从 A 升级到 B?只改 RealOrderClient 内部用的 Adapter(或新建一个 RealOrderClientV2),业务 Workflow / Tool / Critic 一行不用改。整个 Tool 层因为只看 ABC,不知道底下换没换。
4. A/B 切换 / 灰度——同一接口的两套实现并行
生产灰度时要把 10% 流量打到新版 Service,90% 打到旧版?在 ABC 之上加一层路由 ABRoutedOrderClient(old, new, ratio=0.1),业务层照样不知道。
Service ABC 是 5 层架构里最容易被「我们这么简单的项目要这个吗」糊弄过去的一层——但所有「以为简单」的项目,3 个月后都因为缺这一层付出了重写的代价。架构负责人在项目启动那一周就该把 ABC 钉死,不允许任何 Tool 直接 import Adapter。
L3 Tool 层——给 LLM 看的接口契约(不暴露内部结构)
先把结论摆桌面上:Tool 层是 5 层架构里唯一直接面向 LLM 的层——它的 description 和 parameters JSON Schema 决定了 LLM 怎么理解这个能力。Tool 不是 ABC 的别名——它是给 LLM 看的「使用说明」,是 ABC 的「翻译版本」。
一个 Tool 长什么样?拆三件事:
1. description 不是「调用 OMS 接口」,是「查询订单」
错误示范:
ToolDefinition(
name="query_order",
description="调用订单网关的 /orders/list 接口查询订单列表",
)
正确示范:
ToolDefinition(
name="query_order",
description="查询用户的订单。输入 user_id 时返回该用户的所有订单;输入 order_id 时返回该订单的详情。仅返回近 90 天的订单。",
)
为什么? LLM 看到「订单网关」「/orders/list」这种内部实现名,会幻觉出错误的接口——比如它会自己「发明」一个不存在的端点。Tool description 必须是业务语义的描述,不是技术实现的描述。换 OMS 供应商时 description 完全不用改。
2. parameters 是 JSON Schema,不是 Python 类型
parameters = {
"type": "object",
"properties": {
"user_id": {"type": "string", "description": "用户 ID(从 identity 拿,不要从对话文本抽取)"},
"order_id": {"type": "string", "description": "订单 ID,格式 ORD-YYYY-MMDD-XXX"},
},
"required": [], # 二者其一即可,在 execute 里校验
}
注意 description 里显式提醒 LLM 不要从对话文本抽 user_id——这是 D7 安全维度(系列七讲过)的反映。不显式提醒,LLM 看到「用户说我的 ID 是 user_999」会照填。
3. read_only 标志——把读写分开
ToolDefinition(name="query_order", read_only=True) # 读
ToolDefinition(name="query_ticket", read_only=True) # 读
ToolDefinition(name="cancel_order", read_only=False) # 写,必经 Critic
ToolDefinition(name="create_refund", read_only=False) # 写,必经 Critic
read_only=False 的 Tool 由 Workflow 强制要求经过 critic_check Step——不允许 LLM 直接调用写 Tool 不过 Critic。
Tool 层的工程纪律:
- Tool 数量控制在 7-12 个。一个客服 Agent 项目超过 12 个 Tool 通常是 Tool 边界划得太细——「查 7 天内订单」「查 30 天内订单」分两个 Tool 是错的,应该合并成
query_order(time_window_days)。 - 每个 Tool 都有
execute()+ JSON Schema 校验 +ToolResult统一返回值。ToolResult = { success: bool, data: any, error: str | None }。 - Tool 不知道外部系统名。
query_order不知道用的是 OMS A 还是 OMS B;cancel_ticket不知道工单是哪家平台——这些都被 Service ABC 吃掉了。 ToolRegistry统一注册。新增 Tool 时不需要改 LLM prompt 模板,自动 expose 到 LLM 的tools列表。
L4 + L5 Workflow + Critic——写操作的 4 层兜底
先把结论摆桌面上:任何修改外部状态的操作(退款 / 取消订单 / 撤工单),都必须经过 Workflow 编排 + Rules 硬校验 + Critic 语义校验 + 业务签字阈值这四层兜底——少一层就是事故等待发生。
以「小额退款」Workflow 为例,标准的 Step 序列:
small_refund:
Step 1: check_params ← 缺参直接 human_review,不继续
Step 2: query_order ← 拿订单事实
Step 3: validate ← Rules 硬规则:amount ≤ thresholds.max_amount
order_date 在 7 天窗口
24h 内无重复退款
特殊业务类型不放行(biz_type_code 黑名单)
Step 4: critic_check ← LLM Critic 语义校验,fail-closed
Step 5: execute_refund ← 真正调写 Tool(read_only=False)
Step 6: notify ← 给客户发结果
4 层兜底任何一层失效,写操作就降级。架构负责人 review 写 workflow 时核对这张图——validate 没接 Rules / critic_check 没接 LLM Critic / 没走 Service ABC 直调 Adapter——任何一项缺失都是「事故等待发生」。
这套编排里每一层的具体职责:
Workflow 自身的不变量(DSL 层):
- 入口 Step 必须是
check_params,不允许跳过参数校验直接执行 - 写操作 Tool 必须在
critic_checkStep 之后调用 max_steps安全限制(默认 10),防止 LLM 死循环消耗资源human_review=True时立刻退出 workflow,LLM 不能继续推动trigger="event"(定时任务驱动)时抑制 delta 事件——不主动给客户发消息
Rules 层(thresholds.yaml + 代码 RuleEngine):
- 业务方在 docx 签字 → 转
thresholds.yaml→ 代码加载校验。所有金额 / 时间窗口 / 黑白名单都从这里读 - 一处改 → workflow rule + Pydantic
Field(le=...)+/api/rules/thresholds展示同步生效 thresholds.yaml必须有业务方签字版本——不允许研发自己加规则上线
Critic 层(LLM 语义校验):
fail-closed(系列三整篇在讲这件事)——LLM 超时 / 返回格式错误 / API 5xx,全部按「拒绝」处理- 输入 = workflow 已经查到的真实订单事实 + Rules 校验结果;不是用户原始消息
- 输出 =
approve/reject+ 拒绝理由(落到 audit log)
写 Tool 层(实际调外部系统):
- 走 Service ABC → Adapter,LLM 看不到 Adapter
- 整个调用链路 + 入参 + 出参 + 决策依据落 Langfuse trace → 合规审计可查
这 4 层兜底任何一层失效,写操作的安全性就降级。我见过的项目里最常见的塌方点是 Rules 层——业务方没有 docx 签字、研发自己定阈值上线、半年后业务方质疑「这个金额谁定的」。这一条架构负责人要在项目启动时就钉死:所有 Rules 必须有业务 + 法务的 docx 签字版本,不签字的不上线。
6 大外部系统 × 25 个 API——下次架构评审会的拍板清单
先把结论摆桌面上:企业级客服 Agent 项目典型的外部接入是 6 大系统 + 大约 25 个 API。这张清单可以直接当下次架构评审的拍板用——每一行的「分层位置 / 状态 / Owner / 备注」都要在评审会上明确。
| # | 外部系统 | API 类别 | 数量 | 分层位置 | 就绪状态 |
|---|---|---|---|---|---|
| 1-5 | 订单 OMS | list_orders / get_order_detail / cancel_order / get_admin_region / oauth_token | 5 | Adapter ✓ + Service ABC ✓ + Tool ✓ | ✅ 已通 |
| 6 | 订单 OMS | request_refund(与 #14 是否同端点待业务方确认) | 1 | Adapter 待 schema | 🚧 缺定义 |
| 7-9 | 工单平台 | create_ticket / query_ticket / cancel_ticket | 3 | Adapter Stub + Service ABC ✓ + Tool ✓ | 🚧 Stub(schema 待业务方) |
| 10 | 物流提供方 A(主) | track_logistics(签名鉴权) | 1 | Adapter Stub + Service ABC ✓ | 🚧 Stub(签名公式待) |
| 11-13 | 物流提供方 B(备) | track / intercept / receiver_change | 3 | 完全缺 | 🚧 完全无 Adapter |
| 14-15 | 售后系统 | refund_apply / aftersales_status | 2 | Adapter ✓,Workflow 接入待 | 🟡 部分 |
| 16-19 | 公域电商平台(多个主流平台) | order_query / logistics / refund | 4-8 | Mock 契约(业务方未锁定) | 🚧 Mock-only |
| 20-21 | 发票系统 | invoice_status / invoice_issue | 2 | Adapter ✓,Workflow 接入待 | 🟡 部分 |
| 22 | 退差价 FAS | refund_diff | 1 | 完全缺 | 🚧 业务场景待定 |
| 23-25 | 数据稽核看板 | 数据库直读(数据团队 Owner) | 3 | 不在 Agent 范围(数据团队负责) | ➖ 出局 |
| 26 | 客服 IM | webhook + push_message | 1+1 | 入站 Adapter ✓ + 出站 Stub | 🟡 双向中 |
| 27 | 知识库中心 | KB sync + reload | 2 | 内部 KB Center,分层独立 | ✅ 已通 |
| 28 | 仓储 WMS | get_shipment_status(双源验证) | 1 | Stub,fail-closed 转人工 | 🚧 Stub(接口待) |
总计 25-28 个 API,6 大系统——以上是真实项目的接入清单(已脱敏)。架构负责人下次开评审会时把这张表搬出来,每一行问一遍「分层位置在哪?谁是 Owner?Stub 还是真的?业务方签字了吗?」——能在 30 分钟内把项目的真实接入状态摸到底,比看 25 个 API 全绿的 PPT 有用 10 倍。
这张表的颜色分布就是项目「真实接入健康度」的体检报告。红色行多 = 项目还在「接接口」阶段;黄色多 = 已经能跑但 workflow 未联调;绿色密集且分布在核心系统(OMS / KB)= 可以进灰度。架构负责人每两周更新一次。这张表里几条架构负责人必须看出来的信号:
- 「Stub + fail-closed 转人工」是正常状态,不是 bug——WMS 接口还没出来,Adapter 里
StubWmsShippingClient默认返回UNKNOWN,触发fail-closed转人工。这是设计,不是「等接口出来再开发」的借口。 - 「Mock 契约」≠「假数据」——公域电商平台还没确定,但只要 schema 拍板了,QA 可以基于 Mock 跑完所有 E2E 场景。Mock 是 Service ABC 的契约实现,不是「占位假数据」。
- 「不在 Agent 范围」是架构决策,不是缺人——#23-25 数据稽核看板是数据团队的事,Agent 不应该直读业务数据库。这种边界划清楚之后,Agent 团队的 scope 不会无限扩张。
- 「品牌仓 / 特殊业务类型黑名单」要写在
thresholds.yaml——若干biz_type_code(由业务方维护,按业务签字版本加载)触发不放行,业务方在 docx 签字之后才能上线。这种业务规则是 Critic+Rules 层的责任,不是 Tool 层。
这周要推动的 5 件事:让架构落地不再「等供应商」
作为 Agentic 落地负责人,读到这里下周可以推动这 5 件事——任何一件没落地,3 个月后某次供应商变更或合规审计就是事故:
-
画一张「5 层架构 × 6 大系统」的接入矩阵贴在 Confluence。 每个外部 API 落到哪一层(Adapter / Service ABC / Tool / Workflow / Critic)、Owner 是谁、Mock 还是 Real、业务方签字了没——一表全部明确。这张表是「换供应商无痛」的真正基础——表没画清楚,6 个月后某个供应商变更就是 3 周加班。
-
强制研发把所有 Tool import 改成 import ABC,不直接 import Adapter。 这是写代码规范层面的硬约束——一个 grep 就能查出来。
from app.adapters.order_gateway import ...在 Tool 层出现 = 架构违规 = PR 不许进主干。这一条不强制,Service ABC 的所有好处都白搭。 -
把所有写操作 Tool 的 Workflow 都过一遍
critic_checkStep 检查。 写一个简单的脚本扫所有 workflow DSL,确保read_only=False的 Tool 在调用前都有critic_checkStep。没有的 = D7 维度不及格(系列七讲过)= 不允许上线。 -
把
thresholds.yaml拿到业务方 + 法务面前过一遍,要 docx 签字。 金额阈值、时间窗口、特殊业务类型黑名单、商品标签白名单——所有出现在 Rules 层的数字和清单,业务方必须签字、法务必须背书。没签字的 thresholds.yaml 上线就是合规风险。 -
跟外部依赖方对齐 5 个待解的接口 schema: 工单平台出参字段、WMS 发货状态查询、物流签名公式、发票系统端点、公域电商 API。每个待解项指定 Owner + 截止日期 + 阻塞影响。不锁定就意味着 Mock 永远是 Mock,没机会切 Real。
这 5 件事推完,下个月项目对「企业 API 接入」就有了清晰边界——架构评审会上你不再依赖 PPT 上「我们接了 25 个 API」一句话糊弄过去,而是有一张表把每个 API 的分层、Owner、状态、签字都摆出来。这才是企业级 Agentic 该有的样子。
把这一篇的工具带进下一次架构评审会
带客服 Agent 项目这一年最深的体会是:企业级 Agentic 落地的最大成本不在算法、不在模型、不在向量库——是在「外部 API 接入」这一段的分层是否清晰。99% 的项目可以在 3 个月内把 7 个 Tool 通过 demo,但只有把 5 层分层 + 6 大系统 + 25 个 API 矩阵全部画出来的项目,能熬过半年后的第一次供应商变更、第一次合规审计、第一次生产事故。
这一篇的核心是把架构边界变成一张可以贴在评审会白板上的具体清单:5 层职责分工那张表能让你拍板「Adapter 做什么 / Service ABC 做什么 / Tool 做什么 / Workflow 做什么 / Critic 做什么」;6 大系统 × 25 个 API 矩阵能让你 30 分钟看清项目的真实接入状态;4 层写操作兜底能让你在合规审计时拿出完整的调用链;thresholds.yaml 业务签字这条纪律能让你避免 6 个月后业务方质疑「这个阈值谁定的」。
如果你正在带一个企业 Agentic 系统从立项到上线,把这一篇打印出来带到下次架构评审会——多半能省掉一次「换供应商重写半年」的代价。
回复关键词「API 分层」,我把工具包发给你:
- 5 层架构职责清单(Adapter / Service ABC / Tool / Workflow / Critic 各做什么 / 不做什么 / Owner,PDF 一页)
- 6 大系统 × 25 个 API 接入矩阵模板(按你的项目填,直接贴 Confluence)
- Tool 契约 checklist(description / JSON Schema / read_only / 给 LLM 看的语言模板)
- Rules 业务签字模板(thresholds.yaml + docx 签字单 — 业务方 + 法务可以直接用)
回复渠道见页脚(公众号 / X)。不方便回复的,评论区留邮箱也行。
下一篇预告:系列第十篇会拆「一套中文意图体系怎么从 36 演进到 48——corpus → codebook 的标注方法论」。这一篇里反复提到的「48 意图分类」「Layer1 / Layer2 / Layer3 / action / escalate / system / fallback」分层是怎么从 36 个初始意图逐步演进出来的?答案不是「再写一版 prompt」,是让客服话术 corpus、标注员判读、Critic 拦截事件三方共同回流到 codebook——这是 D1 维度上去之前最重要的数据工程决策。
Subscribe for updates
Get the latest AI engineering posts delivered to your inbox.



