第 19 章:企业级部署与运维实操:把原理落成生产系统

第 18 章教"怎么写代码",本章教"怎么上线、怎么运维"。前 6~18 章回答"为什么这样设计才可靠",本章回答"照着这套原理,实际部署一台可信业务智能体要走哪几步"。全程用可操作的分步说明、配置示例与验证方法,配合流程图便于按图索骥。

flowchart TD
    A[环境准备
Python/数据库/密钥] --> B[初始化与降级首跑
无 LLM 也先跑通] B --> C[配置业务规则
第一条硬规则并验证] C --> D[接入审批链与权限
关键操作人机协同] D --> E[可观测与告警
日志/追踪/事件订阅] E --> F[压测与性能验证
延迟预算] F --> G[上线演练与回滚
灰度+回滚预案] G --> H[对照第 18.7 验收清单
逐项核对后放行]

19.1 环境准备:把"要什么"先列齐

原则:环境变量先行,密钥绝不写进代码。 生产部署前准备好下表,缺一项都可能在半路翻车:

项目说明检查要点
Python 运行时框架基于 Python 标准库,推荐 3.10+python --version 确认
业务数据库存放会话状态、审计日志单独只读/读写账号,权限最小化
LLM 接入模型 API Key 或内网网关走环境变量注入,不入代码库
密钥管理API Key / Token / 数据库口令生产用密钥服务,禁止硬编码
部署目录代码 + prog/runtime/ 内嵌框架确认 runtime/ 39 个模块齐全
时钟与网络审计依赖可信时间戳NTP 校准;内网策略放行模型网关

19.2 初始化与降级模式首跑

第 1 步:拉起最小服务(无 LLM、无数据库也能启动)

# 进入项目目录,先跑框架自检
python tests/test_framework.py
# 启动最小服务(降级模式,不注入 LLM/数据库)
python -m prog.runtime.server --config config/minimal.yaml

第 2 步:验证"降级模式"行为(这是第 8.5 节"最小可信实现"的工程落地):

第 3 步:注入真实依赖,逐步升级

# 注入 LLM 与数据库,关闭降级开关
python -m prog.runtime.server --config config/prod.yaml

检验:先降级跑通、再注入依赖,顺序本身就是在验证"哪一层坏了也能降级"。若降级模式都跑不通,说明是代码问题,不是配置问题。

19.3 配置业务规则:第一条硬规则

把"金额必须为正、订单号格式必须合法"这类约束固化为硬规则is_hard=Truebypass=False),模型不可绕过:

from prog.runtime.rule import BaseRule

class AmountPositive(BaseRule):
    def __init__(self):
        super().__init__(
            rule_name="金额必须为正",
            is_hard=True,            # 硬规则:不可绕过
            spec_ref="S-AMT-001",
        )
    def check(self, payload, context):
        amount = payload.get("amount", 0)
        return amount > 0, f"金额 {amount} 必须大于 0"

验证步骤(每一步都要能解释为什么):

验证操作预期结果
1 注册RuleRegistry.register(AmountPositive())注册成功,无报错
2 正向提交 amount=100 的单据校验通过
3 反向提交 amount=-5 的单据校验拦截,返回 blocked 与原因
4 绕过测试尝试构造不带该规则的通道硬规则在所有写操作前执行,无法绕过

要点:规则验证是"生产前最值得花时间的 10 分钟"。每条规则都值得做一次正向 + 一次反向验证,并留档(spec_ref)供审计追溯。

19.4 接入审批链与权限:关键操作人机协同

第 1 步:定义审批流程(定义与实例分离,改流程不影响运行中的实例):

from prog.runtime.approval import ApprovalChain, Gate
chain = ApprovalChain([
    Gate("发起校验", check=lambda ctx: ctx.user.role in {"manager", "finance"}),
    Gate("金额阈值", check=lambda ctx: ctx.payload["amount"] <= 100_000),
    Gate("复核签字", human=True),   # 人工节点,必须人确认
])

第 2 步:接权限体系(角色 + 属性双重判定):

from prog.runtime.security import PermissionSystem
perm = PermissionSystem()
perm.grant("query_order", roles=["sales", "manager", "finance"])
perm.grant("create_order", roles=["manager"], attrs={"dept": "sales"})

第 3 步:上线前模拟一次完整流程:发起 → 阈值校验 → 人工确认 → 留痕 → 查审计日志确认"谁批的、依据哪条规则"。审批链没跑通,不接入生产

19.5 可观测与告警:让系统"自己说话"

from prog.runtime.events import bus
bus.subscribe("rule.blocked", lambda e: alert(e))   # 规则拦截告警
bus.subscribe("approval.pending_timeout", lambda e: alert(e))

告警阈值建议(起步值,按运行一周后校准):规则拦截率周环比波动超过 ±30% 告警;审批平均处理时长超过目标 2 倍告警;模型调用失败率 > 1% 告警。

19.6 压测与性能验证:先证明"快且对"

第 1 步:设延迟预算(从 SLO 倒推,见 17.4.2)。例如"查询接口 P95 < 3 秒",分解为:规则校验 20ms + 意图识别 200ms + 模型调用 2.5s + 尾部缓冲。

第 2 步:并发正确性验证(正确性优先于性能):

第 3 步:压测与回归

# 用 ab 或 wrk 打流量,观察 P95 与错误率
ab -n 5000 -c 50 http://localhost:8080/api/query
# 压测后重跑降级模式全量测试,确认性能优化未破坏正确性
python tests/test_framework.py

结论范式:只有"并发下结果依然正确"的压测才有意义——这正是第 17 章标题"正确性是性能的前提"的落地。

19.7 上线演练与回滚:把"出问题怎么办"提前想好

灰度三步

  1. 先接入 1 个低风险场景(如周报查询)→ 观察一周准确率与告警;
  2. 再接入 1 个写操作场景(带审批链)→ 观察审批流与审计完整性;
  3. 全部平稳后再逐步放量。

回滚预案(演练中至少跑通一次)

上线门禁:对照第 18.7 章验收清单逐项核对(正确性 / 契约 / 路由 / 状态 / 规则 / 安全 / 流程 / 训练 / 记忆 / 可观测 / 性能 / 测试),全绿才放行。

19.8 本章小结

阶段核心动作关键检验对应原理
准备列齐环境变量与密钥无硬编码密钥第 12 章
初始化降级模式首跑无 LLM 也正确第 8 章
规则第一条硬规则反向用例被拦截第 11 章
审批权限审批链 + 权限人工节点生效留痕第 13 / 12 章
可观测日志 / 追踪 / 告警单一 trace_id第 16 章
压测延迟预算 + 并发并发下仍正确第 17 章
上线灰度 + 回滚 + 验收验收清单全绿第 18 章

一句话记住本章:第二部的原理(生成 × 裁决、规则、审批、审计、可观测、并发)不是纸面设计,而是每一步都有可验证操作的部署流程——按本章顺序做完一遍,就等于把 6~18 章的原理全部落到了生产环境。