Files
cma-management/docs/bot-write-tiering-20260903.md
Hermes CI Fix 9a823e80a6 test(bot-tier): UI实证脚本 SuggestionCenter 默认未应用+类型过滤 (P0-②)
CDP登录→/ai-suggestions→待批列表默认unapplied且可见Bot建议卡+过滤芯片DOM全命中
临时建议SUG_ID=300已清理(回查0)
2026-09-03 18:19:58 +08:00

77 lines
7.7 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Bot 写操作分级 + 分层授权审计清单(2026-09-03)
> 任务: P0-② CMA Bot写操作分级 + 分层授权落地(低危直写留痕 / 高危建议待批)
> 依据: CMA交互架构规范_三区分工模型_v1.md 第5节 + 5.1 分层授权模型(任总 2026-09-03 拍板)
> 代码权威注释: backend/app/risk_levels.py 文件头「写操作语义分级」段
> 配套端点: backend/app/api/bot_suggestions.py(新增,Bot高危建议创建通道)
## 一、两套分级的正交关系(防误读)
| 维度 | 名称 | 作用 | 载体 |
|---|---|---|---|
| 技术风险分级 | L1 只读 / L2 业务写 / L3 批量写 / L4 危险不开放 | 约束操作面、批量、写前校验 | `API_RISK_MAP` + `@risk_level` 装饰器 |
| 业务写语义分级 | **low**(规则型数据写,Bot直写+留痕) / **high**(考核基准/资源承诺,Bot只能建议) | 约束"写的是不是考核基准",落地为行为约束 | 本清单 + 代码注释 |
关系:**low = 现有 L2/L3 直写端点行为不变;high = Bot API面不提供直写端点,只走建议通道端点(本身按 L2 标注)**。本任务未替代、未改动 L1-L4 体系,只在其上补业务语义约束。
## 二、端点审计清单(Bot API面全量)
### 只读(L1,无写语义,不属于 low/high)
- GET /api/cma/bot/ping · overview · kpis · kpis/{kpi_id}/history · strategic-maps · alerts · budget/plans · cost/standard · cost/actual · actions · organization · data-sources · users · query · okr/list · nlp · iron-law · iron-law/bots · risk-levels
- GET /api/cma/bot-kpis
- GET /api/cma/bot-bridge/verify/{action_plan_id}/history
### low = Bot 直写 + 留痕(规则型、写库即生效;audit_log.bot_audit_middleware 全量覆盖 /api/cma/bot* 路径)
| 端点 | L级 | 写什么 | 留痕机制 | 归类依据 |
|---|---|---|---|---|
| POST /api/cma/bot/kpi-value-with-check | L2 | KPI实际值(upsert)+联动预警 | audit_log + source_type=bot | 数据搬运,规则明确 |
| POST /api/cma/bot-bridge/kpi-result | L2 | KPI实际值(upsert) | audit_log + source_batch=source | 同上(PRD第七部分数据通道) |
| POST /api/cma/bot-kpis/{kpi_id}/value | L2 | KPI实际值(upsert) | audit_log | Bot KPI看板值更新 |
| POST /api/cma/bot/import | L3 | Excel批量导入KPI实际值 | audit_log + rows | 批量数据导入 |
| POST /api/cma/bot-bridge/mpm-result | L3 | MPM结果→KPI实际值 | audit_log + rows | 批量分析结果落库 |
| POST /api/cma/bot-bridge/verify/{action_plan_id} | L2 | 轻量验证记录(verify_log,无回填) | audit_log | 行动方案验证状态 |
| POST /api/cma/bot/okr/create | L2 | 创建OKR Objective | audit_log | 管理类业务写(目标创建,保留评审:列P1待办) |
| POST /api/cma/bot/kpis/create-with-links | L3 | 创建新KPI定义+因果链 | audit_log + rows | 建KPI标准动作(**本任务收口见下**) |
### high = 建议通道(无直写端点,人审批后生效)
| 端点 | L级 | 语义 | 生效路径 |
|---|---|---|---|
| POST /api/cma/bot/ai/suggestions(**本任务新增**) | L2 | Bot创建 kpi_target/budget_adjust/action_plan 建议,status 恒 unapplied | UI AI建议中心(SuggestionCenter.vue)→ 人 apply → /api/cma/ai/suggestions/{id}/apply 写库 + apply_detail(before/after) + applied_by/applied_at |
## 三、直写 KPI 目标值/预算审批端点审计结论(grep 实证)
1. **KPI 目标值直写**:grep `target_value|目标值` 全 backend/app —— bot_bridge.py / bot_bridge_v2.py / bot_kpis.py 中 `target_value` 仅出现在**读响应**(查询返回 kpi.target_value)与**验证引擎**(value>target 比较),**无任何修改现有 KPI target_value 的 Bot 端点**。存量 KPI 目标修改只经 `/api/cma/ai/suggestions/{id}/apply`(require_auth 人token)。
2. **收口项(发现并处理)**:`POST /api/cma/bot/kpis/create-with-links` 原允许 payload 带 `target_value` 随新建 KPI 一并写入(Bot 间接直写初始目标值=考核基准)。**2026-09-03 已收口**:传入非零 target_value → 400 明确拒绝,指引省略(人工设定)或走建议通道;0/省略不受影响。
3. **预算审批直写**:Bot API面预算相关端点仅 GET /api/cma/bot/budget/plans(只读);budget.py / budget_generate.py 均挂在人工 require_role 路由下。Bot 无任何预算写端点。
4. **阈值类(红黄绿)**:监测参数类(Bot建议+人批量确认)本轮**未开放 Bot 直写也未开放批量确认 UI**——列入 P1 待办(见六),不阻塞本单验收。
## 四、高危审批留痕闭环(M3 实证结论)
- kpi_target applier(ai_suggestions.py `_apply_kpi_target`)已含 before→after 留痕:apply_detail=[{target_type,target_id,target_name,action,before,after}] 写入 ai_suggestions.apply_detail,同时写 OperationLog(detail 含 suggestion_id/before/after);apply_suggestion 置 status=applied + applied_by/applied_user_id/applied_at。**无需补代码**(E2E 断言验证)。
- SuggestionCenter.vue:默认展示 unapplied(statusFilter 默认 'unapplied')+ 新增 suggestion_type 过滤(全部/kpi_target/budget_adjust/action_plan),小改无重构。
## 五、留痕链路(低危直写)
- bot_audit_middleware(backend/app/api/audit_log.py)对路径前缀 /api/cma/bot* 全部请求写 JSON 行至 backend/logs/bot_audit.log,字段: timestamp/bot_name/endpoint/method/risk_level/entity_id/status(L3 额外 rows)。
- 覆盖: /api/cma/bot、/api/cma/bot-bridge、/api/cma/bot-kpis、/api/cma/bot/ai/suggestions(新增,自动覆盖)。
- /kpi-result 写入 KPIValue 带 source_batch=source(bot_bridge_v2.py:465 existing.source_batch = source)→ KPIValue.source_batch 落库可追溯。
## 六、P1 待办(不阻塞本单验收)
1. **阈值类批量确认 UI**:alert_rules 红黄绿阈值"Bot建议+人批量确认(一次5-10条)"——需阈值建议通道+批量 apply 端点+UI,改动面大,单列任务。
2. **OKR Objective 创建**归口评审:okr/create 是否应降级为建议通道(OKR=战略承诺,边缘属考核基准类);本轮保留 L2 直写并在 risk_levels.py 注释中列示待评审。
3. **suggestion 来源 UI 标注**:source='bot'/'rule' 的来源标签补充(前端 sourceLabel 已加 bot: 'Bot建议')。
4. **审计清单文档同步巡检**:新增 Bot 写端点时应同步本清单与 risk_levels.py 头部注释(当前为手工维护,防止漂移)。
## 七、验收记录(E2E/回归)
- 回归: backend/tests/test_bot_suggestion_channel.py(12条:鉴权/语义/多租户/幂等/审批闭环/审计/收口);test_risk_levels.py 计数更新 L2=6。
- 生产E2E: backend/scripts/verify_bot_write_tiering_e2e.py(可复跑,标记+清理+回查)2026-09-03 全 PASS:
A Bot创建kpi_target建议→unapplied → B 人apply→KPI目标100→888.88 + apply_detail(before/after) + applied_by=管理员/applied_at → C /kpi-result 直写 source_batch=e2e-bot-tier-20260903 落库 → D bot_audit.log 两条 L2 记录(财务BOT / bot-bridge)→ E 清理回查=0。
- UI实证: backend/scripts/verify_suggestioncenter_unapplied_ui.py(CDP,9225)2026-09-03 全 PASS:
登录→/ai-suggestions→待批列表默认 status=unapplied 且可见 Bot建议卡片(E2E-验证,临时建议验证后删除),类型过滤芯片(全部类型/改KPI目标/调预算/建行动方案)与状态radio(未应用/已应用/已忽略)在DOM命中。
- pytest 全量: 726 passed / 4 failed(日历漂移预存:budget roll_forward + ai_suggestions budget_overrun + roadmap budget_headroom×2,非本次回归) / 1 xfailed。
- 后端重启: systemctl restart cma-backend(ActiveEnter 晚于 commit); /health ok。