dev-manager-tauri/.blueprint/modules/project-capability-control-plane.md
lanrtop 8bc33aaab9
All checks were successful
Push & PR Check / check (push) Successful in 1m18s
Push & PR Check / check (pull_request) Successful in 58s
fix(delivery): distinguish skipped production deploy
2026-09-23 11:08:10 +09:00

360 lines
26 KiB
Markdown
Raw 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.

---
id: project-capability-control-plane
name: 项目能力与交付控制面
status: in_progress
progress: 0
---
## 概述
炼境是被管理项目的工程管家,而非项目业务大脑或通用 CI 替代品。项目拥有业务规则、测试、迁移和部署要求;炼境保存云端环境与凭证引用,执行受控操作,采集运行证据。Enterprise System 是首个真实样板。
## 设计决策:项目能力协议与轻量交付控制面 v1
### 背景
Enterprise System 已有可用的云端交付基础:Gitea `main` CI 通过 SSH 调用服务器端 `deploy/deploy-api.sh`;脚本用 Git SHA 标记镜像,在停止旧容器前做环境/网络/镜像检查,切换后做容器内 HTTP 健康闸门,失败自动回滚,且保留近期镜像与 Gitea registry 回滚池。其关键缺口不是再造部署脚本,而是让 Agent 可安全发现、请求、验证和追溯这条能力。
### 方案选择
| 方案 | 说明 | 结论 |
| --- | --- | --- |
| 炼境直接内置每个项目的部署命令 | 快,但把项目细节、环境差异和业务风险硬编码进平台 | 否决 |
| 项目声明能力,炼境以 adapter 执行 | 项目保持自主,凭证与审计集中,能复用到异构项目 | **选定** |
| 强制所有 commit 经 PR/CI 后再部署 | 治理完整但阻塞 Agent 高频真实环境验证 | 否决;仅 production/高风险路径强制 |
### 系统边界
```
项目(Enterprise System)
声明 verify/build/migrate/deploy/health/logs/rollback 的输入与成功断言
保留 Dockerfile、migration、部署脚本和业务终验
炼境控制面
保存环境、凭证引用、允许项目/目标、部署记录和运行证据
通过 SSH / Docker Compose 等 adapter 执行受控动作
Gitea adapter
提供 SHA、PR、少量 CI 与 release 依据;不是炼境核心依赖
Codex / Claude adapter
读取项目规则与能力声明,调用炼境 MCP;不持有生产凭证
```
### 交付节奏
1. Agent 完成本地验证后小步 commit;多个相关 commit 汇成一个可说明的 PR/交付包。
2. 普通内部功能在 PR 合并后沿既有 Gitea CI 自动部署 production;炼境先采集版本、CI、健康与回滚证据,不替换项目部署脚本。
3. 涉及公共引擎、跨业务线、数据写路径或 migration 的改动进入 PR;Gitea CI 只保留高价值检查,并要求在 PR 中说明备份或回滚方式。
4. 炼境只呈现信号和执行受控操作,不判断业务是否“应该上线”;没有可验证的部署回传时必须明确标为 `unknown`。
### 协议草案
项目 canonical context 采用工具无关位置 `.lian-jing/context.json`;现有 `.claude/liangjing.json` 与 Codex 配置是派生兼容层。项目能力声明建议位于 `.lian-jing/capabilities.yaml`:
```yaml
version: 1
capabilities:
verify:
command: pnpm verify
deploy:
targets:
production:
adapter: ssh-script
environment_ref: enterprise-production
revision: git_sha
command: bash deploy/deploy-api.sh
requires_confirmation: true
health:
checks:
- kind: http
url_ref: enterprise-api
expect_status: 401
```
声明不得包含 IP、SSH 私钥、数据库 URL 或 Secret。`environment_ref` 由炼境映射到加密保存的环境事实;adapter 命令采用 allowlist/模板参数,禁止 Agent 任意拼接远程 shell。
### 证据与失败模型
一次 deployment record 至少包含:`project_id`、`environment`、`requested_revision`、`resolved_sha`、`requester`、`started_at`、`finished_at`、`migration_set`、`adapter_result`、`health_evidence`、`previous_healthy_release`、`rollback_result`。任何外部源不可用都显式标为 unavailable/error,不能伪装成“无 PR”或“部署成功”。
### 验证路径
- 炼境:`cargo test` 直接调用 Git/Gitea 状态归并纯函数,断言脏工作区、无绑定、网络不可达和缺失部署证据均可诚实降级。
- Enterprise System:继续使用现有 production 部署脚本及其健康闸门/回滚;本阶段不把 production 当作自动测试路径。
- MCP:`get_delivery_status(project_id)` 返回本地 Git、Gitea、CI、review 与可取得的部署/health 来源状态,无错误字段时每项均可追溯。
### 现有链路的兼容策略
Enterprise System 当前 `push main → Gitea CI → deploy-api.sh` 是 production 链路,且服务器资源有限。本阶段保持该链路不动,也不引入常驻 staging。`get_delivery_status` 不将 CI 成功误报为线上健康;后续若线上验证成本或事故频率证明有必要,再以独立资源或按需环境增加 staging adapter。
### 风险点
- migration 非向后兼容:v1 不自动执行任意 migration;先读取项目声明、预检与锁定策略,production 必须人工确认。
- 无 staging 的生产验证风险:普通改动依赖本地验证、PR 和现有自动回滚;高风险 migration/关键数据改动要求备份和显式交付说明。
- Git SHA 与服务器工作树漂移:adapter 输出必须解析/回传 resolved SHA,且 health 证据绑定同一记录。
- 现有部署健康闸门仅证明 HTTP 监听:协议同时支持项目声明业务 health probe,不把存活探测误报为业务就绪。
- Gitea/网络故障:交付状态明确降级;项目本地验证与项目自有手工部署能力不受炼境阻断。
## 设计决策:production 交付观测 v1(2026-09-22,已确认)
### 背景与本轮收敛
P1 已能读取本地 Git、PR、CI 与 review,但 `deployment` 仍固定为 `unknown`。Enterprise System 的真实链路已经是 `push main → Gitea Actions → SSH → deploy-api.sh → 容器内健康闸门/失败回滚`;服务器资源有限,不适合为了治理额外常驻一套 staging,也没有必要由炼境重做部署脚本。
本轮目标只解决一个问题:让人和 Agent 都能回答“生产当前运行哪个 SHA、最近一次部署是否成功、技术健康是否可达”,同时保持现有自动部署链路完全不变。第一版明确不提供部署、回滚、migration 或任意远程命令执行能力。
### 方案选择
| 方案 | 优点 | 缺点 | 结论 |
| --- | --- | --- | --- |
| 只读取 Gitea Actions/commit status | 实现最小,不接触服务器 | 只能证明 job 结果,不能证明此刻运行的版本;回滚后尤其可能误报 | 不单独采用 |
| 炼境通过只读 SSH 查询 Docker | 能直接读取镜像与容器状态 | 需要生产凭证、耦合服务器命令与 Docker,扩大攻击面并把平台过早变成运维执行器 | 后置,不进入 v1 |
| Gitea 部署信号 + 服务版本探针双证据 | 既有部署过程证据,也有实时运行 SHA/健康证据;无需 staging 与 SSH | 需 Enterprise System 增加极小的公开只读端点,并把 SHA 烘焙进镜像 | **选定** |
### 数据流与信任边界
```text
Enterprise System main push
└─ Gitea Actions deploy-api job
├─ 现有 deploy-api.sh:构建、切换、健康闸门、失败回滚(保持所有权)
└─ Gitea commit status:目标 SHA 的部署过程证据
Enterprise production API
└─ GET /health/version
└─ 当前容器镜像内烘焙的 revision + technical health
炼境 get_delivery_status(project_id)
├─ 读取 Gitea 部署 context
├─ 读取项目声明的只读 health/version probe
└─ 纯函数归并:目标 SHA、运行 SHA、部署状态、技术健康、漂移
├─ MCP 投影:Codex / Claude
└─ Tauri 投影:项目交付状态面板
```
Gitea 是“部署过程事实源”,运行服务是“当前线上事实源”。只有最新部署 context 成功、版本探针健康且 `running_revision == target_revision` 时,聚合状态才可为 `deployed`。任一证据缺失必须保留为 `unknown` / `unavailable`;CI 成功不得替代部署成功,HTTP 存活也不得替代业务验收。
### 项目声明与外部契约
项目继续拥有能力声明。建议在 `.lian-jing/capabilities.yaml` 增加只读 delivery profile;该文件只允许声明公开 HTTP(S) 探针和 Gitea context 名称,不允许认证头、Token、SSH 命令、IP 凭证或数据库连接串:
```yaml
version: 1
delivery:
targets:
production:
provider: gitea-actions
components:
api:
deploy_context: deploy-api
probe:
kind: http-json
url: https://api3.yljt.info/health/version
revision_field: revision
healthy_field: ok
```
Enterprise System 新增未鉴权只读端点:
```json
GET /health/version
{
"ok": true,
"component": "api",
"revision": "<git-sha>",
"started_at": "<iso-8601>"
}
```
`revision` 必须在 Docker build 时写入镜像(例如 build arg → image ENV),不能在启动脚本里总是注入“本次请求 SHA”;否则部署失败后回滚旧镜像时会把旧代码伪报成新 SHA。端点不得返回环境变量、主机信息、数据库状态或其他敏感内容。
### `get_delivery_status` 兼容演进
保留现有顶层 `DeliveryStatus` 结构,不新增破坏性字段;扩展 `deployment.data`:
```json
{
"environment": "production",
"target_revision": "<sha>",
"running_revision": "<sha>",
"deployed_at": "<gitea-status-time>",
"components": {
"api": {
"deploy": { "state": "success", "source": "gitea" },
"health": { "state": "healthy", "source": "http_probe" },
"revision_match": true
}
},
"evidence": []
}
```
稳定状态语义:
- `not_configured`:项目没有 production delivery profile。
- `pending`:部署 context 尚未到达最终状态。
- `deployed`:部署成功、探针健康、运行 SHA 与目标 SHA 一致。
- `drifted`:本次部署 context 成功、探针可达,但运行 SHA 与目标 SHA 不一致(含回滚后的旧版本)。
- `skipped`:本次默认分支提交未触发部署;保留实际运行 SHA,不把正常跳过误报为漂移或部署成功。
- `failed`:Gitea 明确报告部署失败;若探针仍健康,必须同时展示实际运行 SHA,不能把线上误报为不可用。
- `unhealthy`:运行 SHA 可读但技术健康失败。
- `unknown`:缺少足以判断的证据。
- `unavailable`:已配置来源当前不可达。
v1 不新增 deployment history 表。最近部署时间和过程状态来自 Gitea status 的时间字段,当前运行事实来自实时探针;连续历史、受控部署和审计记录等真实需求出现后,再评估 SQLite record。
### 系统边界变更
- **Enterprise System HTTP 契约**:新增 `/health/version`;Docker 镜像携带不可变 revision,回滚镜像自然恢复对应旧 revision。
- **项目能力声明**:新增只读 delivery profile schema;onboarding 只提供示例/校验,绝不覆盖项目已写声明。
- **炼境聚合层**:`delivery_status.rs` 读取 profile、Gitea deployment context 与 HTTP 探针,归并逻辑保持纯函数可测。
- **Rust 本体与 MCP 投影**:Tauri command 与 MCP 复用同一个 Rust 业务函数;首轮只交付 MCP 可读闭环,UI 等 2~4 周观测证明收益后再决定是否补充。
- **无数据库与执行面变更**:v1 不新增凭证、环境授权、deployment record、SSH adapter、staging 或发布按钮。
### 受影响文件
- 修改:`src-tauri/src/commands/delivery_status.rs` — deployment 双证据聚合与稳定状态。
- 修改:`src-tauri/src/commands/gitea.rs` — 保留 deployment context 的时间、target URL 与原始状态;实现前先用真实 Gitea 1.22 payload 校准 context 名称。
- 修改:`src-tauri/src/mcp_tools.rs`、`src-tauri/src/mcp_server.rs` — MCP schema/dispatch 与协议测试。
- 修改:`src-tauri/src/commands/onboarding.rs`、`src-tauri/resources/onboarding/` — capability profile 示例与只读自检,不覆盖项目定制。
- 后置:`src/lib/commands.ts`、项目治理面板 — 不进入首轮 MVP;只有观测证明能减少人工确认或故障定位时间时再补。
- 消费者修改:`E:/code-project/enterprise-system/apps/api/src/index.ts`、`apps/api/Dockerfile`、`deploy/deploy-api.sh`、`.lian-jing/capabilities.yaml` — 版本探针、镜像 revision 和 production profile。
### 验证路径
- 载体:Tauri command / MCP(炼境)+ HTTP API(Enterprise System)。
- 示例:`[HTTP API] GET https://api3.yljt.info/health/version → 200,ok=true,revision 为当前镜像 SHA,且无敏感字段`。
- 示例:`[cargo test] aggregate_deployment_signal(target_sha, gitea_success, probe_same_sha) → state=deployed;probe_old_sha → state=drifted;Gitea 不可达 → unavailable;证据缺失 → unknown`。
- 示例:`[MCP] get_delivery_status(enterprise_project_id) → deployment.data 同时列出 Gitea 与 runtime 两类 evidence;两者一致才返回 deployed`。
- 首轮不设置 UI `human_verify`;真实 production 验收只读取现有部署结果,不新增人工发布步骤。
### 风险点与约束
- Gitea 1.22 status context 命名可能与 job 名不同:实现前必须读取一次真实 `/statuses/{sha}` payload 固化 fixture,不凭 workflow 文件猜测。
- HTTP 探针可能被 DNS、代理或短暂网络故障影响:设置短超时与响应体大小上限;网络失败返回 unavailable,不覆盖最后一次 Gitea 部署事实。
- 探针 URL 来自已注册项目声明,但仍只接受 `http/https`,禁止 `file:` 等协议、认证头和动态 Agent 入参,避免把工具变成任意请求代理。
- `ok=true` 只代表项目定义的技术健康,不代表业务流程验收通过;UI 与 MCP 文案必须保留这条边界。
- 多组件部署可能部分成功:数据结构支持 components,但首个消费者只落地 API;Web 的版本探针待真实需要后扩展。
### 确认后的 MVP 拆解(2026-09-22)
用户确认采用“先证明 Agent 能准确判断某个 SHA 是否真正在线,再决定是否补 UI”的薄 MVP,共 5 张 S/M 卡:
1. Gitea 1.22 真实 deployment signal 实证与归一化。
2. Enterprise System 不可变 revision + `/health/version`。
3. production delivery profile、安全探针读取与 onboarding 自检。
4. deployment 双证据聚合与 MCP 契约。
5. 经用户批准的既有 production 流程端到端验收,并建立 2~4 周观测基线。
## 本轮范围调整
- B/C/G 保留为远期 concept:只有四周观测证明“只读状态”仍不能降低失败定位或回滚成本时,才评估环境授权、SSH adapter 与受控 production 操作。
- E/F 取消:用户已明确服务器资源有限,不建设常驻 staging;未来若资源或事故数据改变,再新建独立迭代,不作为 P3 依赖。
## 任务卡
### ✅ A. Canonical 项目上下文与 capability schema
- status: done
- complexity: M
- files: src-tauri/src/mcp_inject.rs, src-tauri/src/commands/onboarding.rs, src-tauri/src/mcp_tools.rs, src-tauri/resources/onboarding/, docs/templates/agents-meta-rules.md
- acceptance: "[cargo test] 旧 `.claude/liangjing.json` 项目重跑接入 → 写入 `.lian-jing/context.json`,project_id 一致;Claude/Codex adapter 均从 canonical context 派生且保留用户手工同名配置;无 canonical context 时给出可诊断兼容状态。"
- done_note: "2026-09-22:由 agent 复核确认与 P2-A 同一能力,canonical context、legacy 迁移、未知字段保留、手工同名 MCP 拒绝覆盖及诊断信号已在 PR #8/#9 完成;cargo test 139/139 与 Enterprise onboarding 12/12 已通过。"
### 💭 B. 炼境环境、授权与 deployment record 数据模型(远期)
- status: concept
- depends: A. Canonical 项目上下文与 capability schema
- files: src-tauri/src/db.rs, src-tauri/src/models.rs, src-tauri/src/commands/
- acceptance: "[cargo test] in-memory DB 创建 environment / project authorization / deployment record 后,未授权项目、production 未确认、同环境并发请求均被拒绝;record 可记录 requested_sha、resolved_sha、health_evidence 与 previous_healthy_release。"
- note: "P3 只读观测不需要新表;待真实执行/历史审计需求出现后再升格。"
### 💭 C. SSH-script adapter 与生产环境锁(远期)
- status: concept
- depends: B. 炼境环境、授权与 deployment record 数据模型
- files: src-tauri/src/commands/, src-tauri/src/lib.rs, src/lib/commands.ts
- acceptance: "[Tauri command] deploy_production(project_id, revision, confirmation) 对 mock SSH adapter → 仅接受声明中的 adapter/command,写入 running→succeeded|failed record;同一 environment_ref 第二次调用返回锁定状态,绝不执行第二条远程命令。"
- note: "v1 不持有 SSH 执行权;只读双证据运行四周后再评估。"
### ✅ P1. 交付状态与 Gitea 轻量治理投影
- status: done
- complexity: M
- files: src-tauri/src/commands/gitea.rs, src-tauri/src/mcp_tools.rs, src-tauri/src/mcp_server.rs, docs/ai-context/
- acceptance: "[MCP tool] get_delivery_status(project_id) → 返回当前 SHA/工作树、PR/CI/review 来源状态与 deployment/health evidence 的已知或 unknown 状态;Gitea 不可达时标记 unavailable 而非把 PR 误报为空;cargo test 通过纯函数/命令级降级测试。"
- done_note: "2026-09-21:MCP schema/dispatch、Git/Gitea 聚合、接入说明和降级测试完成;production 部署回传尚未接入,按协议显式返回 unknown。"
### E. Enterprise System 可选 staging 隔离与部署 profile
- status: abandoned
- depends: A. Canonical 项目上下文与 capability schema, C. SSH-script staging adapter 与环境锁
- files: E:/code-project/enterprise-system/deploy/deploy-api.sh, E:/code-project/enterprise-system/deploy/README.md, E:/code-project/enterprise-system/.gitea/workflows/, E:/code-project/enterprise-system/.env.api.example
- acceptance: "agent_verify: [future isolated staging] 部署已 push SHA → 使用与 production 不同的 environment_ref、服务器目录/容器名/域名/运行时配置,resolved SHA 和 health evidence 可读取;不触发既有 `push main` production job;human_verify: staging 关键业务接口可用。仅当资源与实际线上验证成本证明必要时启动。"
- abandoned_reason: "2026-09-22 用户确认服务器资源有限,当前追求快速开发与快速 production 部署;不建设常驻 staging。"
### F. Enterprise System capability 声明与可选 staging 适配验证
- status: abandoned
- depends: E. Enterprise System 可选 staging 隔离与部署 profile
- files: E:/code-project/enterprise-system/.lian-jing/, E:/code-project/enterprise-system/deploy/README.md, E:/code-project/enterprise-system/.blueprint/
- acceptance: "agent_verify: [炼境 staging adapter] 请求 Enterprise System 已 push SHA → 只匹配声明的 staging profile,服务器输出 resolved SHA,容器 health gate 与项目声明的 HTTP probe 均通过,炼境 record 绑定同一 SHA;human_verify: staging 关键业务接口可用。"
- abandoned_reason: "随 staging 方案一并取消;production 只读 profile 将在设计确认后由 splitter 另拆。"
### 💭 G. production 发布确认、回滚与操作报告(远期)
- status: concept
- depends: C. SSH-script adapter 与生产环境锁(后续受控执行), P1. 交付状态与 Gitea 轻量治理投影
- files: src-tauri/src/commands/, src-tauri/src/mcp_tools.rs, src-tauri/src/commands/gitea.rs, E:/code-project/enterprise-system/deploy/
- acceptance: "[cargo test] deploy_production 缺显式 confirmation 或 required CI/PR evidence → 无远程执行;[adapter integration] health gate 失败 → record 标 failed 并保存 rollback result / previous release,生产成功记录含确认者与 resolved SHA。"
- note: "从 P3 的观测指标决定是否需要升格;不再依赖已取消的 staging 卡。"
### ✅ P3-A. Gitea 1.22 真实 deployment signal 实证与归一化
- status: done
- complexity: M
- files: src-tauri/src/commands/gitea.rs, E:/code-project/enterprise-system/.gitea/workflows/ci.yml
- depends: P1. 交付状态与 Gitea 轻量治理投影
- acceptance: "[cargo test] 使用脱敏后的真实 Gitea 1.22 `/statuses/{sha}` payload 运行 deployment signal 归一化测试 → success/pending/failure、context、updated_at、target_url 与目标 SHA 均被保留,无关 CI context 不得误判为部署;若真实 payload 不含独立 deploy signal,则由既有 workflow 发布稳定 context 后用同一测试通过。"
- done_note: "2026-09-22:通过炼境 MCP 实证 Gitea 1.22.6 为 run #525/#529 发布独立 context,API 为 `CI — DeepSeek Agent / deploy-api (push)`;保留 target SHA、target_url、created_at/updated_at,并发现/修复 skipped job 被编码为 status=success + description=Has been skipped 的误判风险。既有 workflow 无需修改;cargo test --lib 全量通过,实机 get_delivery_status 已将 run #529 deploy-api/deploy-web 正确归一化为 skipped。"
### ✅ P3-S1. 炼境自身 Codex 接入闭环
- status: done
- complexity: M
- files: AGENTS.md, .claude/commands/envoy.md, .agents/skills/lian-jing/SKILL.md, .codex/config.toml, .lian-jing/context.json, .lian-jing/capability-packs.json
- acceptance: "agent_verify: [MCP] `get_diagnostics()` 返回本地服务状态;`verify_onboarding(dev-manager-tauri)` → canonical context、Codex skill、MCP 与能力包全部 ready;`get_delivery_status(dev-manager-tauri)` → 能读取 PR #13 的 SHA、CI 与 review。不得从旧 `.claude/liangjing.json` 猜测身份或提取 Gitea token。"
- done_note: "2026-09-22:通过既有 inject_mcp 迁移旧上下文,apply_onboarding_pack 升级托管基线,verify_onboarding 11/11;经 MCP 实测读取 PR #13(SHA 0141b8b、CI passed),用户确认后由 merge_pull_request 合并,合并后开放 PR 状态为 none。当前 Codex 任务不支持热加载新 MCP 配置,原生客户端发现留待新任务验证。"
### ✅ P3-S2. Agent PR 合并安全门禁
- status: done
- complexity: M
- depends: P3-S1. 炼境自身 Codex 接入闭环
- files: src-tauri/src/commands/gitea.rs, src-tauri/src/mcp_tools.rs, docs/ai-context/git-workflow.md, src-tauri/resources/onboarding/git-workflow.md.tmpl, src-tauri/resources/onboarding/.agents/skills/lian-jing/SKILL.md, src-tauri/resources/onboarding/.lian-jing/capability-packs.json, plugins/lian-jing-codex/skills/lian-jing/SKILL.md
- acceptance: "agent_verify: [cargo test] `merge_pull_request` 在 confirmed=false、expected_head_sha 与远端不一致、PR 非 open、CI pending/failure 或 review changes_requested 时拒绝且不执行 merge;仅在 PR open、SHA 一致、CI passed、无阻塞 review 且 confirmed=true 时允许执行;[MCP schema] confirmed 与 expected_head_sha 均为必填;合并后重新调用 get_delivery_status 可读取真实结果。"
- done_note: "2026-09-22:cargo test --lib 151/151、pnpm typecheck 与 PR CI 全部通过;MCP 实机先以错误 SHA 验证 fail-closed,再由用户确认 PR #14 与完整 head SHA b6d749025458928b86ab607a5a7f31479f8db85f 后,通过带 head_commit_id 的能力本体成功合并;回读 get_delivery_status 为 PR none、CI passed。"
### 🔵 P3-B. Enterprise System 不可变 revision 与版本健康端点
- status: in_progress
- complexity: M
- files: E:/code-project/enterprise-system/apps/api/src/index.ts, E:/code-project/enterprise-system/apps/api/Dockerfile, E:/code-project/enterprise-system/deploy/deploy-api.sh
- acceptance: "[HTTP API] 以 BUILD_REVISION=<sha-a> 构建并启动 API 镜像后调用 `GET /health/version` → 200,body 仅含 ok/component/revision/started_at 且 revision=<sha-a>;切回以 <sha-b> 构建的旧镜像 → revision=<sha-b>,证明回滚不会伪报新 SHA。"
- progress_note: "Enterprise 隔离分支 feat/production-revision-evidence 本地提交 d915399;API typecheck、bash 静态检查与隔离端口 HTTP 四字段/鉴权冒烟通过。Docker daemon 未运行,新旧镜像回滚和 production 仍待验,故保持 in_progress。"
### 🔵 P3-C. production delivery profile、安全探针与 onboarding 自检
- status: in_progress
- complexity: M
- files: src-tauri/src/commands/delivery_status.rs, src-tauri/src/commands/onboarding.rs, src-tauri/resources/onboarding/
- depends: A. Canonical 项目上下文与 capability schema
- acceptance: "[cargo test] 读取声明了 production/http-json probe 的 capability profile → 得到固定 environment/component/context/url 字段;`file:`、URL 内凭证、动态认证头、超时响应和超限响应体分别被拒绝或降级为 unavailable;未配置项目返回 not_configured,onboarding 自检不覆盖已有声明。"
### 🔵 P3-D. deployment 双证据聚合与 MCP 契约
- status: in_progress
- complexity: M
- files: src-tauri/src/commands/delivery_status.rs, src-tauri/src/mcp_tools.rs, src-tauri/src/mcp_server.rs
- depends: P3-A. Gitea 1.22 真实 deployment signal 实证与归一化, P3-C. production delivery profile、安全探针与 onboarding 自检
- acceptance: "[MCP] `get_delivery_status(project_id)` 对固定 fixture 调用 → Gitea success + probe healthy + SHA 相同返回 deployed;成功部署但 SHA 不同返回 drifted;deploy skipped 且运行旧 SHA 返回 skipped;deploy failure 同时保留实际运行 SHA;来源不可达返回 unavailable;证据不足返回 unknown,且现有 Git/PR/CI/review 顶层字段保持兼容。"
- progress_note: "2026-09-23:真实 Enterprise run #529 的 deploy-api 为 skipped;聚合层新增 skipped 与旧运行 SHA 回归测试,避免普通文档提交误报 drifted。隔离分支 cargo test --lib 187/187;正式版尚未加载新代码,production 探针当前为 401,待 PR/发布后做 MCP 端到端验收。"
### 📋 P3-E. Enterprise production 端到端验收与观测基线
- status: todo
- complexity: M
- files: E:/code-project/enterprise-system/.lian-jing/capabilities.yaml, E:/code-project/enterprise-system/deploy/README.md, docs/ai-context/agent-button-system.md
- depends: P3-B. Enterprise System 不可变 revision 与版本健康端点, P3-D. deployment 双证据聚合与 MCP 契约
- acceptance: "agent_verify: [HTTP API + MCP] 经用户批准合并并由 Enterprise 既有 main workflow 部署后,`GET https://api3.yljt.info/health/version` 的 revision 与目标 commit SHA 一致,`get_delivery_status(enterprise_project_id)` 返回 deployed 且同时列出 Gitea/runtime evidence;不触发炼境 SSH、部署、回滚或数据库写入。随后记录 2~4 周人工确认次数、失败定位时间与漂移发现数,未证明收益前不新增 UI。"
## 迭代衡量
首个版本上线后连续观察四周:commit 至 production 部署结果可追溯的时间、production 前实际拦截问题数、失败定位与回滚耗时、PR 等待时间、Agent 重复劳动/上下文丢失次数。不能降低任一真实成本的门禁或自动化应降级或移除。