From 4efb28443e3f78312b15ead0b99e8916cf212709 Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 01:39:50 +0000 Subject: [PATCH 01/13] Record the task card for feature-super-admin Why: establish the authorized task workspace and its initial baseline. Evidence: preserved precheck receipt in .task/feature-super-admin.md; R0=d9ac28f89159e17781e2a8ef3094965130f29d2f. Impact: task metadata only; the feature workspace starts at d9ac28f89159e17781e2a8ef3094965130f29d2f. Refs: .task/feature-super-admin.md --- .task/feature-super-admin.md | 154 +++++++++++++++++++++++++++++++++++ 1 file changed, 154 insertions(+) create mode 100644 .task/feature-super-admin.md diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md new file mode 100644 index 00000000..f12025b7 --- /dev/null +++ b/.task/feature-super-admin.md @@ -0,0 +1,154 @@ +# feature/super-admin 任务卡 + +任务主记录:;状态:进行中;owner:weichen + +## 基线与授权 + +- 权威仓:ssh://git@git-ssh.u1680832.nyat.app:31411/weichen/Agent-System-Dev.git;目标分支:main;R0(initial_base_sha)= d9ac28f89159e17781e2a8ef3094965130f29d2f +- 工作区:/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin(worktree);分支:feature/super-admin +- 分支类型:standalone;root_target:main;immediate_target:main;accepting_requirements:false +- 需求分流:verdict=NEW;selected_initiative=无;requirement_sha256=6d60f1f804e671045b7a395a470576eb8d89a9f30dda4b80885921b5296ca639;triage_receipt=/tmp/task-triage-super-admin.json;receipt_sha256=0018c29af8c89053d28c7163733bb37e4c9c21e344541bf805a8745f886b9048 + +- 授权与交付终点:<本次允许的动作与终点;未授权事项写明> +- 交付模式:goal-first(目标、范围和交付终点一次确认;范围内连续推进) +- 实施执行:agent-per-unit(配置:AGENT-EXECUTION.md) +- 合入执行:agent(已授权交付范围内,Review 通过、冲突解决且当前 HEAD 的 CI 通过后合入) +- 人工决策点:仅限目标/范围/验收变更、重大取舍、高后果操作或无法自动判定的业务验收 +- 当前阶段:需求拆解;当前增量:I1(待定义) +- 流程依据:仓库根目录 policy/delivery.md(归档后仍按仓库根目录定位) + +## 目标与非目标 + +<预期结果、受影响入口/模块/契约;明确不做什么。> + +## Agent 实施收据 + +路由与 fail-stop 规则见根目录 AGENT-EXECUTION.md 与 policy/delivery.md;每次尝试一行,原始日志留在源码外收据路径。 + +| 单元 ID | 预期范围 | 配置摘要 | 角色 | 候选顺序 | attempt | CLI/模型 | 终态 | transport | fallback | 源码外收据路径 | +|---|---|---|---|---|---|---|---|---|---|---| +| 待定义 | — | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | + +## 关联方向与规划 + +- 适用状态:待核对(无适用规划时说明原因) +- 主记录路径/版本:待核对(路径按仓库根目录定位,归档后不变;只引用唯一正文) +- 对应里程碑:待核对 + +## 需求分析 + +| ID | 描述 | 项目符合度及依据 | 优先级 | 验收条件 | 依赖 | 结论 | +|---|---|---|---|---|---|---| +| R1 | 待填写 | 待评估 | 待定 | 待定义 | 待确认 | 待评审 | + +## 方案与计划 + +- 方案引用:待填写(含对象版本) +- 实施计划引用:待填写(含增量与需求 ID) +- 测试计划引用:待填写(含需求 ID 与验收条件) + +## 阶段记录 + +| 阶段 | 对象版本 | 状态 | 决策/执行者 | 时间 | 依据 | +|---|---|---|---|---|---| +| 需求拆解 | 待定 | 待执行 | — | — | — | +| 需求评估 | 待定 | 待执行 | — | — | — | +| 需求表确认 | 待定 | 待执行 | — | — | — | +| 方案设计 | 待定 | 待执行 | — | — | — | +| 实施计划 | 待定 | 待执行 | — | — | — | +| 实施与自检 | 待定 | 待执行 | — | — | — | +| 正式测试与验收 | 待定 | 待执行 | — | — | — | +| 代码 Review | 待定 | 待执行 | — | — | — | +| 合入 | 待定 | 待执行 | — | — | — | +| 合入核验与收口 | 待定 | 待执行 | — | — | — | + +## 探索试验与迭代 + +| 增量/试验 | 假设 | 范围 | 判断和停止条件 | 授权/决策依据 | 结果 | 变更影响 | 需重审补测 | +|---|---|---|---|---|---|---|---| +| 待定义 | — | — | — | 待核对 | NOT_RUN | 待评估 | 待评估 | + +## 同步记录 + +| 节点 | sync_base_sha | tested_head_sha | checked_at | +|---|---|---|---| +| 启动 | d9ac28f89159e17781e2a8ef3094965130f29d2f | d9ac28f89159e17781e2a8ef3094965130f29d2f | 2026-10-19T01:39:50Z | + +## 证据(Evidence) + + +| 时间(UTC) | 命令 | 被测HEAD | exit | 来源 | sha256(16) | +|---|---|---|---|---|---| + +## 交付调度 + +- 调度状态:未入队;调度记录:无 +- entry_id:无;attempt_id:无;窗口执行者:无 +- 固定候选:无(base/head、组件与相关配置引用实际尝试) +- 调度依据:policy/delivery.md#合入调度 +- 固定后证据:源码外 RECEIPT;实际结果后按授权原样导入和闭合 + +## 结果与验证(完成后填写) + +- 结果: +- 验证:<结论摘要 PASS/FAIL/SKIP/NOT_RUN 逐项;逐条证据由 make evidence 写入上方证据表> +- 影响与剩余项: + +## 规划进展与下一步 + +- 本次推进/剩余:待核对(依据实际成果更新适用方案/规划) +- 首选下一任务:待核对(无适用规划、已完成或受阻时如实说明,不虚构任务) +- 推荐依据:待填写 +- 前置条件/待确认:待核对 +- 预期产物/验收条件:待定义 +- 重复任务核对:待核对(已有/在途任务、PR 与规划记录) +- 启动授权:未授权(建议不自动启动新任务,仍须明确授权) + +## 合入与清理 + +- Review 记录:NOT_RUN(审阅智能体/平台身份、base/head、结论、问题闭合及重放依据) +- 冲突记录:NOT_RUN(最新目标同步、冲突处置、组合兼容核验及复审/补测) +- CI 记录:NOT_RUN(当前 HEAD 完整 SHA、全部必需检查、运行链接、执行身份及 GATE 结果) +- 合入记录:NOT_RUN(交付授权范围、PR、被核验 HEAD、合入 SHA、目标分支及内容核验) +- 清理记录:NOT_RUN(授权依据、写者退出确认、worktree/分支/任务卡处置) + + +```json +{ + "summary_schema": 1, + "source": "SELF", + "timestamp": "2026-10-19T01:38:39.334481+00:00", + "command": "make precheck", + "exit_code": 0, + "cwd": "/home/weichen/projects/Agent-System-Dev", + "before_head": "d9ac28f89159e17781e2a8ef3094965130f29d2f", + "after_head": "d9ac28f89159e17781e2a8ef3094965130f29d2f", + "branch": "main", + "target_branch": "main", + "target_head": "d9ac28f89159e17781e2a8ef3094965130f29d2f", + "root_target": "main", + "immediate_target": "main", + "before_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "after_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "output_tail": [ + "make[1]: Entering directory '/home/weichen/projects/Agent-System-Dev'", + "[repo] branch=main head=d9ac28f891", + "[remote] origin/main=d9ac28f891 ahead=0 behind=0", + "[tree] clean submodules_drift=0 uninit=13", + "[warn] 13 个子模块未初始化——构建/测试前需物化(不阻断写入)", + "[worktrees] linked=4", + "[recycle] merged un-recycled branches: feature/layered-python-env", + "[initiatives] local cards (not authoritative): none", + "[hooks] core.hooksPath=scripts/hooks(pre-commit/post-merge 实际接线)", + "[facts] policy/facts.md 6 条事实均在有效期内", + "[required-reading] core/baseline.md, workflows/delivery.md §1, policy/delivery.md", + "[R0] d9ac28f891(完整:d9ac28f89159e17781e2a8ef3094965130f29d2f)", + "[worktree] before-sync: recursive component checks passed", + "[verdict] READY — 保留本次 precheck receipt 后建任务工作区:PRECHECK_RECEIPT=/tmp/task-precheck.json make task-start NAME=feature/your-branch", + "make[1]: Leaving directory '/home/weichen/projects/Agent-System-Dev'" + ], + "output_sha256": "7e6162d2d8f8c775defedcb6fcfcaa4db8342ab302a5354f7b6233687922997b", + "receipt_sha256": "c657e9c3dd3c1b526ad5b5a50c0616d534812d3a753c436db4daefaa23b55446", + "receipt_path": "/home/weichen/.cache/agent-system-dev/evidence/c657e9c3dd3c1b526ad5b5a50c0616d534812d3a753c436db4daefaa23b55446.json" +} +``` From 5fa2ecbc74ecb373bdef1f023d01da56d515d09b Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 01:41:12 +0000 Subject: [PATCH 02/13] Initialize super-admin plan and task card Why: Set up the task card and approved implementation plan for environment-configured super-admin. Evidence: make precheck and task-start validated. Impact: Establishes task metadata and implementation baseline. Refs: #0 --- .task/feature-super-admin.md | 63 +++++---- .../plans/2026-10-19-0113-super-admin-plan.md | 124 ++++++++++++++++++ 2 files changed, 165 insertions(+), 22 deletions(-) create mode 100644 docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md index f12025b7..cb980295 100644 --- a/.task/feature-super-admin.md +++ b/.task/feature-super-admin.md @@ -1,6 +1,6 @@ # feature/super-admin 任务卡 -任务主记录:;状态:进行中;owner:weichen +任务主记录:待提 PR;状态:进行中;owner:weichen ## 基线与授权 @@ -9,17 +9,26 @@ - 分支类型:standalone;root_target:main;immediate_target:main;accepting_requirements:false - 需求分流:verdict=NEW;selected_initiative=无;requirement_sha256=6d60f1f804e671045b7a395a470576eb8d89a9f30dda4b80885921b5296ca639;triage_receipt=/tmp/task-triage-super-admin.json;receipt_sha256=0018c29af8c89053d28c7163733bb37e4c9c21e344541bf805a8745f886b9048 -- 授权与交付终点:<本次允许的动作与终点;未授权事项写明> +- 授权与交付终点:用户 2026-10-19 要求“按照方案开始实施”,依据 docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md。范围:将超级管理员建模为独立身份,覆盖 .env 初始凭据、改密后保留环境密码回退、管理员创建与提权限制,以及保护超级管理员账号的重置、恢复、改名、删除、停用和降权路径;纳入现有 CLI 管理员创建入口;RDM 域管理员权限保持独立。终点:完成 U1~U4 四个实施单元,通过对应单元测试、数据库测试、浏览器端验证、独立 Review、代码合入与安全清理。凭据不入仓。 - 交付模式:goal-first(目标、范围和交付终点一次确认;范围内连续推进) - 实施执行:agent-per-unit(配置:AGENT-EXECUTION.md) - 合入执行:agent(已授权交付范围内,Review 通过、冲突解决且当前 HEAD 的 CI 通过后合入) - 人工决策点:仅限目标/范围/验收变更、重大取舍、高后果操作或无法自动判定的业务验收 -- 当前阶段:需求拆解;当前增量:I1(待定义) +- 当前阶段:实施与自检;当前增量:U1~U4 - 流程依据:仓库根目录 policy/delivery.md(归档后仍按仓库根目录定位) ## 目标与非目标 -<预期结果、受影响入口/模块/契约;明确不做什么。> +- 目标: + 1. 通过 .env 中 SUPER_ADMIN_OWNER 与 SUPER_ADMIN_PASSWORD 配置唯一的超级管理员身份(R1, R2); + 2. 超级管理员改密后,支持新密码与 .env 回退密码登录,且回退密码不持久化(R6, R7); + 3. 超级管理员可创建管理员或提权普通账号;普通管理员只能创建普通用户,所有服务端提权与管理创建路径均拦截普通管理员(R3, R4); + 4. 保护超级管理员账号免受普通管理员重置、恢复、改名、删除、停用或降权,现有 CLI 创建入口纳入统一限制(R5); + 5. UI 界面展示超级管理员身份并按权限显示管理员创建/提权控件(R8)。 +- 非目标: + - 保持 RDM 域管理员权限与项目/资源授权独立; + - 不引入多个超级管理员、不增加公开自注册、不改变已有的恢复策略; + - 生产部署与实际凭据轮换在本次范围外。 ## Agent 实施收据 @@ -27,40 +36,50 @@ | 单元 ID | 预期范围 | 配置摘要 | 角色 | 候选顺序 | attempt | CLI/模型 | 终态 | transport | fallback | 源码外收据路径 | |---|---|---|---|---|---|---|---|---|---|---| -| 待定义 | — | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | +| dev-superadmin-u1-bootstrap | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/store/account_model.go, modules/backend/internal/store/migrate.go, modules/backend/internal/server/server.go, scripts/svc.sh | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | +| dev-superadmin-u2-login-fallback | modules/backend/internal/server/accounts.go, modules/backend/internal/store/auth.go, modules/backend/internal/server/auth.go, modules/backend/internal/server/login_recovery_test.go | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | +| dev-superadmin-u3-privilege-protection | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/server/accounts.go, modules/backend/internal/server/roles.go, modules/backend/internal/store/account_model.go, modules/backend/internal/store/role_policy.go, modules/backend/internal/authz/ | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | +| dev-superadmin-u4-ui-surface | modules/backend/internal/server/accounts.go, modules/frontend/src/components/AdminZone.tsx, modules/frontend/src/components/AccountUsersPanel.tsx, modules/frontend/src/components/adminSections.tsx, modules/frontend/e2e/admin-user-create.playwright.ts, modules/frontend/e2e/iam-role-authority.playwright.ts | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | ## 关联方向与规划 -- 适用状态:待核对(无适用规划时说明原因) -- 主记录路径/版本:待核对(路径按仓库根目录定位,归档后不变;只引用唯一正文) -- 对应里程碑:待核对 +- 适用状态:独立实施计划已完成评审(docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md) +- 主记录路径/版本:docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md +- 对应里程碑:U1(配置与引导)→ U2(回退登录与改密)→ U3(权限边界与保护)→ U4(UI 界面) ## 需求分析 | ID | 描述 | 项目符合度及依据 | 优先级 | 验收条件 | 依赖 | 结论 | |---|---|---|---|---|---|---| -| R1 | 待填写 | 待评估 | 待定 | 待定义 | 待确认 | 待评审 | +| R1 | .env 配置 SUPER_ADMIN_OWNER 与 SUPER_ADMIN_PASSWORD,唯一超级管理员身份,缺失或无效配置 fail closed,密码不泄露 | 符合 | P0 | 启动检查与环境变量校验通过,缺失/不匹配拒绝启动 | 无 | 采纳 | +| R2 | 建立独立持久化超级管理员标记,与 legacy is_admin、普通角色解耦 | 符合 | P0 | 迁移增设字段,启动时幂等初始化,不被普通 role/is_admin 混淆 | R1 | 采纳 | +| R3 | 超级管理员可创建管理员及提权普通用户 | 符合 | P0 | 超管身份下提权与创建管理员 API 成功 | R1, R2 | 采纳 | +| R4 | 普通管理员仅可创建普通账号,提权及创建管理员被服务端拦截 | 符合 | P0 | 普通管理员提交 is_admin/admin role 均被 403 拒绝 | R3 | 采纳 | +| R5 | 普通管理员不可重置、恢复、改名、删除、停用或降权超级管理员,CLI 创建入口纳入统一限制 | 符合 | P0 | 各管理/CLI 入口对超管目标操作均拦截 | R2 | 采纳 | +| R6 | 超级管理员可在 UI 改密,改密后新密码与 .env 回退密码均可登录,回退密码不落库 | 符合 | P0 | 登录校验支持双凭据,改密后旧库密失效、新库密与环境变量密均可登入 | R1, R2 | 采纳 | +| R7 | 超级管理员登录失败遵循原有限流与会话版本策略,审计与安全策略完整 | 符合 | P0 | 登录限流、审计事件与会话版本测试通过 | R6 | 采纳 | +| R8 | 前端界面展示超级管理员标识,仅向超级管理员暴露提权/管理员创建控件 | 符合 | P0 | 前端 AccountUsersPanel/AdminZone 条件渲染,直接 API 调用亦受服务端保护 | R3, R4 | 采纳 | ## 方案与计划 -- 方案引用:待填写(含对象版本) -- 实施计划引用:待填写(含增量与需求 ID) -- 测试计划引用:待填写(含需求 ID 与验收条件) +- 方案引用:docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md +- 实施计划引用:docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md § Implementation Units (U1~U4) +- 测试计划引用:docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md § Verification Contract ## 阶段记录 | 阶段 | 对象版本 | 状态 | 决策/执行者 | 时间 | 依据 | |---|---|---|---|---|---| -| 需求拆解 | 待定 | 待执行 | — | — | — | -| 需求评估 | 待定 | 待执行 | — | — | — | -| 需求表确认 | 待定 | 待执行 | — | — | — | -| 方案设计 | 待定 | 待执行 | — | — | — | -| 实施计划 | 待定 | 待执行 | — | — | — | -| 实施与自检 | 待定 | 待执行 | — | — | — | -| 正式测试与验收 | 待定 | 待执行 | — | — | — | -| 代码 Review | 待定 | 待执行 | — | — | — | -| 合入 | 待定 | 待执行 | — | — | — | -| 合入核验与收口 | 待定 | 待执行 | — | — | — | +| 需求拆解 | d9ac28f891 | 已完成 | host / 用户授权 | 2026-10-19T01:40:00Z | 用户指令及计划文档 | +| 需求评估 | d9ac28f891 | 已完成 | host | 2026-10-19T01:40:00Z | 计划文档 R1~R8 | +| 需求表确认 | d9ac28f891 | 已完成 | host | 2026-10-19T01:40:00Z | 计划文档 | +| 方案设计 | d9ac28f891 | 已完成 | host | 2026-10-19T01:40:00Z | 2026-10-19-0113-super-admin-plan.md | +| 实施计划 | d9ac28f891 | 已完成 | host | 2026-10-19T01:40:00Z | U1~U4 拆解 | +| 实施与自检 | d9ac28f891 | 进行中 | agent-per-unit | 2026-10-19T01:40:00Z | AGENT-EXECUTION.md | +| 正式测试与验收 | 待定 | 待执行 | host | — | — | +| 代码 Review | 待定 | 待执行 | 独立会话 | — | — | +| 合入 | 待定 | 待执行 | host | — | — | +| 合入核验与收口 | 待定 | 待执行 | host | — | — | ## 探索试验与迭代 diff --git a/docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md b/docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md new file mode 100644 index 00000000..ecb0e570 --- /dev/null +++ b/docs/superpowers/plans/2026-10-19-0113-super-admin-plan.md @@ -0,0 +1,124 @@ +--- +title: Environment-configured super administrator +date: 2026-10-19 +type: plan +artifact_contract: ce-unified-plan/v1 +product_contract_source: ce-plan-bootstrap +execution: code +--- + +## Goal Capsule + +- **Objective:** The system has one environment-configured super administrator who can appoint system administrators, while administrators can create ordinary accounts but cannot elevate accounts or reset the super administrator's password. +- **Means:** Add an explicit super-administrator identity and apply its authority in server-side authentication and account-management checks (KTD1). +- **Authority:** The user request in this session; preserve current project and RDM domain authorization boundaries. +- **Execution profile:** Implement in bounded Backend and Frontend units, with focused SQLite/PostgreSQL tests and browser coverage for changed account-management flows. +- **Stop conditions:** Stop when the requirements and direct verification pass. Do not change RDM domain-admin authority, general recovery policy, deployment state, or unrelated role capabilities. +- **Delivery owner:** Host owns planning, scope review, integration, authoritative verification, review, PR/CI, and safe closure under repository policy; implementation units use the configured agent-per-unit route. + +## Product Contract + +### Summary + +Configure a single highest-privilege system administrator using credentials supplied through `.env`. This account may create administrator accounts or promote an existing account. Other administrator accounts may create ordinary accounts only and cannot reset the super administrator's password. The super administrator may change their password in the product; the configured environment password remains a separate fallback login credential. + +### Problem Frame + +The system currently has `is_admin` accounts and delegated system actions, but no distinct super-administrator identity. That makes it impossible to reserve administrator appointment and super-administrator protection to one bootstrap authority while retaining ordinary administrator account creation. + +### Requirements + +- R1. In authentication-enabled account-management deployments, exactly one system super-administrator identity is configured by `SUPER_ADMIN_OWNER` and `SUPER_ADMIN_PASSWORD` in the process environment sourced from the protected `.env` configuration. Missing, partial, invalid, or unavailable configuration must fail closed with a clear startup error; the unauthenticated embedded single-user mode must not expose account-administration operations. Secret values must never be logged or returned by APIs. +- R2. The configured identity is established as a distinct super-administrator in persistent account state. It is never inferred from legacy `is_admin`, a role, a project membership, or RDM domain-admin state. +- R3. The super administrator can create ordinary accounts and can create administrator accounts or promote an existing account to administrator. +- R4. An ordinary administrator can create ordinary accounts, but every server-side path that creates or grants administrator authority rejects that actor, regardless of UI visibility or supplied request fields. +- R5. An ordinary administrator cannot reset, recover, rename, delete, disable, or demote the super-administrator account through account-management or CLI paths. Ordinary administrators cannot change their own or another account's administrative authority through account creation, role assignment, system-grant APIs, or CLI commands. The super administrator can change their own password through R6 but cannot remove or transfer the unique super-administrator identity through product account-management paths. +- R6. The super administrator can change their password through the existing authenticated password-change flow. The changed password and configured environment fallback password both authenticate that same identity; changing the database password does not remove the fallback. +- R7. Failed super-administrator password checks follow the existing login throttling and session-version rules. Successful login and password changes continue to use HttpOnly sessions and existing credential/audit safeguards. +- R8. The UI identifies the super administrator and exposes administrator creation/promotion controls only to that identity. Server authorization remains authoritative. + +### Scope Boundaries + +- Preserve existing RDM domain-admin separation and project/resource authorization. +- Do not add multiple super administrators, self-registration, a new recovery channel, an alternate CLI administrator-bootstrap path, or production deployment/migration operations. +- Do not reduce unrelated permissions of delegated users beyond the account-elevation and super-administrator-protection rules in R4-R5. + +## Planning Contract + +### Key Technical Decisions + +- KTD1. **Model super-administrator as a separate system identity flag.** Keep `is_admin` for compatibility and ordinary system-admin behavior, while a dedicated persisted marker identifies the single highest-privilege account. `is_admin` remains true for the super administrator, but never implies super-administrator status. +- KTD2. **Use the database password and environment fallback as two valid credentials for the configured owner.** Verify both only for the super-administrator identity, retain the environment secret only in process memory, and never overwrite it when the UI changes the database password. +- KTD3. **Enforce privilege boundaries on the server and within account-write transactions.** Apply one consistent super-admin-aware authorization rule to account creation, role assignment, system-grant changes, state changes, resets, and recovery entry points that can affect administrator or super-administrator authority. +- KTD4. **Bootstrap idempotently and fail closed on identity conflict.** Startup may establish the configured account and its initial password when absent or uninitialized; if the owner already belongs to another account or a second super-admin marker exists, startup must stop instead of silently promoting, replacing credentials, or creating a second authority. + +### High-Level Technical Design + +Backend startup reads the two required settings from `.env` through the supported runtime environment-file path, validates them, and passes an immutable secret-bearing configuration object into account initialization and the authentication service. The database stores the designated account identity and the ordinary password hash; the configured fallback is not persisted. Login checks the normal password hash first, then the fallback only when the requested owner matches the configured super administrator. Account authorization resolves the persisted marker from trusted server state and applies actor/target constraints before each write. Frontend account screens consume a server-provided `isSuperAdmin` field and conditionally show the elevation controls. + +The Backend currently reads configuration from process environment but no dotenv parser was found. U1 must verify the actual service launcher and make its protected `.env` values available to the Backend through that supported runtime path. If no such path exists, add one narrowly scoped `.env` loading mechanism at the existing configuration boundary; do not silently fall back to missing credentials or duplicate parsing across modules. + +### Assumptions + +- `SUPER_ADMIN_OWNER` is a stable account identifier; renaming it or transferring super-admin authority is outside this change. +- `.env` remains protected from source control and has restrictive filesystem permissions in deployments. +- If the fallback secret is exposed, an operator must rotate `SUPER_ADMIN_PASSWORD` in `.env` and restart the service; the UI password change does not revoke this fallback. +- Existing account password hashing, password policy, lockout, session revocation, and audit mechanisms remain the authoritative primitives. + +## Implementation Units + +### U1. Configure and bootstrap the single super administrator + +- **Goal:** Load validated super-administrator settings and establish exactly one persistent super-administrator identity without silently taking over a conflicting account. +- **Requirements:** R1, R2 +- **Files:** `modules/backend/cmd/agent-system/main.go`, `modules/backend/internal/app/`, `modules/backend/internal/store/account_model.go`, `modules/backend/internal/store/migrate.go`, `modules/backend/internal/server/server.go`, `scripts/svc.sh` +- **Approach:** Trace and wire the protected `.env` startup path; pass credentials via a dedicated config boundary; add a schema migration and idempotent bootstrap operation; reject account-admin operations when authentication is disabled; keep secrets out of persistent storage, diagnostics, and JSON projections. +- **Test Scenarios:** Both values absent, only one present, invalid password, first bootstrap, repeated bootstrap, conflicting existing owner, duplicate marker, and legacy databases with administrators but no super administrator. +- **Verification:** Focused Backend config, store migration/bootstrap, and startup tests on SQLite and PostgreSQL. + +### U2. Add fallback login and password-change behavior + +- **Goal:** Let the configured super administrator authenticate with either the database password or the `.env` fallback, including after changing the database password in the UI. +- **Requirements:** R6, R7 +- **Files:** `modules/backend/internal/server/accounts.go`, `modules/backend/internal/store/auth.go`, `modules/backend/internal/server/auth.go`, `modules/backend/internal/server/login_recovery_test.go` +- **Approach:** Extend the login verifier at the authentication boundary; fallback comparison is limited to the configured super-admin owner; retain current rate limiting, verified-session version checks, and normal password-change behavior. +- **Test Scenarios:** Initial environment password works; UI password change makes both new and fallback passwords valid; old database password stops working; fallback fails for every other owner; disabled/missing account and throttled attempts remain rejected. +- **Verification:** Focused login/password tests covering password-change session handling and audit effects, plus existing account serialization tests where verifier changes affect session races. + +### U3. Enforce super-admin-only appointment and target protection + +- **Goal:** Restrict admin creation/promotion to the super administrator and make the super-administrator account untouchable by ordinary admin maintenance paths. +- **Requirements:** R3, R4, R5 +- **Files:** `modules/backend/cmd/agent-system/main.go`, `modules/backend/internal/app/`, `modules/backend/internal/server/accounts.go`, `modules/backend/internal/server/roles.go`, `modules/backend/internal/store/account_model.go`, `modules/backend/internal/store/role_policy.go`, `modules/backend/internal/authz/` +- **Approach:** Audit every account/admin elevation and target mutation route, including `user create --admin`, `user create --role admin`, and `user bootstrap-admin`; only configured startup bootstrap may establish the super administrator, and no CLI path may appoint another administrator. Enforce actor and target checks in the authorization/write boundary, including transactional rechecks for race safety. Preserve the ordinary-admin path for creating pending user accounts. +- **Test Scenarios:** Super admin creates/promotes admin; ordinary admin creates user; ordinary admin cannot create/promote admin by request payload, role assignment, grants, or CLI commands; neither ordinary admin nor legacy admin can reset/recover/rename/delete/disable/demote the super admin; super admin can change their own password but cannot transfer or remove the unique super-admin identity; auth-disabled mode exposes no account-administration operations; unauthorized and concurrent changes are rejected without partial writes. +- **Verification:** Focused account, role-policy, and recovery authorization tests on SQLite and PostgreSQL. + +### U4. Surface identity and available account actions in the UI + +- **Goal:** Make super-administrator status and allowed administrator-management actions clear in account-management screens. +- **Requirements:** R3, R4, R8 +- **Files:** `modules/backend/internal/server/accounts.go`, `modules/frontend/src/components/AdminZone.tsx`, `modules/frontend/src/components/AccountUsersPanel.tsx`, `modules/frontend/src/components/adminSections.tsx`, `modules/frontend/e2e/admin-user-create.playwright.ts`, `modules/frontend/e2e/iam-role-authority.playwright.ts` +- **Approach:** Add a non-secret `isSuperAdmin` identity projection and show admin-create/promotion actions only for that user. Keep ordinary account creation available to authorized admins and avoid exposing environment credentials or fallback status details. +- **Test Scenarios:** In the primary `AccountUsersPanel`, super admin sees admin-promotion controls and can complete promotion; ordinary admin sees ordinary-account creation without elevation controls; direct API calls remain rejected when controls are hidden; layout remains usable at supported viewport sizes. +- **Verification:** Focused Frontend typecheck and Playwright coverage for the account-management flow. + +## Verification Contract + +| Scope | Verification | Proves | +|---|---|---| +| Backend account/auth changes | Focused `go test` packages under `modules/backend/internal/server`, `internal/store`, `internal/app`, and `cmd/agent-system` | Bootstrap, dual-credential login, account elevation boundaries, and compatibility | +| Database portability | Relevant PostgreSQL integration tests in the affected Backend packages | Migration/bootstrap and transactional authorization behavior on PostgreSQL | +| UI behavior | Focused Frontend typecheck and admin-user Playwright tests | Correct controls and browser-visible account flow | +| Final candidate | `make test` when required by the selected delivery tier and exact repository gate | Fixed Dev/component composition and repository-required checks | + +No production deployment or live `.env` credential test is included in this plan. Runtime acceptance requires a separately authorized environment and must use test credentials without recording secret values. + +## Definition of Done + +- Exactly one environment-configured super administrator can be established, and startup rejects ambiguous or conflicting identity state. +- The super administrator can appoint administrators; other administrators can create ordinary accounts but cannot grant administrative authority. +- Ordinary administrators cannot mutate the super-administrator account through supported account-management or recovery paths. +- The super administrator can change the database password in the UI and can continue to log in with the configured fallback. +- Server tests, affected database coverage, focused browser verification, code review, and repository delivery gates pass for the exact candidate; secrets are absent from logs, responses, and committed files. +- Abandoned implementation attempts are removed, and no production deployment, credential rotation, or history-changing action is performed without its required authorization. From bdfb5e85e5ccf4188d68b8967bd6e1a12189109e Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 01:46:26 +0000 Subject: [PATCH 03/13] Record PR link in task card Why: Reference PR #627 in the active task card. Evidence: make task-pr-check OK. Impact: Task metadata references the open PR. Refs: #627 --- .task/feature-super-admin.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md index cb980295..a9132ad9 100644 --- a/.task/feature-super-admin.md +++ b/.task/feature-super-admin.md @@ -1,6 +1,6 @@ # feature/super-admin 任务卡 -任务主记录:待提 PR;状态:进行中;owner:weichen +任务主记录:PR #627 https://git-home.u1680832.nyat.app:30319/weichen/Agent-System-Dev/pulls/627;状态:进行中;owner:weichen ## 基线与授权 From 70b00d1302a7325269714dcb75ccab1b6cfe8cee Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 03:37:32 +0000 Subject: [PATCH 04/13] Record super-admin implementation units in task card Why: Update task card unit table with U1-U4 completed runs and receipts. Evidence: Receipts generated under ~/.cache/agent-system-dev/evidence/. Impact: Task card metadata update only. Refs: #627 --- .task/feature-super-admin.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md index a9132ad9..664c27e1 100644 --- a/.task/feature-super-admin.md +++ b/.task/feature-super-admin.md @@ -36,10 +36,10 @@ | 单元 ID | 预期范围 | 配置摘要 | 角色 | 候选顺序 | attempt | CLI/模型 | 终态 | transport | fallback | 源码外收据路径 | |---|---|---|---|---|---|---|---|---|---|---| -| dev-superadmin-u1-bootstrap | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/store/account_model.go, modules/backend/internal/store/migrate.go, modules/backend/internal/server/server.go, scripts/svc.sh | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | -| dev-superadmin-u2-login-fallback | modules/backend/internal/server/accounts.go, modules/backend/internal/store/auth.go, modules/backend/internal/server/auth.go, modules/backend/internal/server/login_recovery_test.go | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | -| dev-superadmin-u3-privilege-protection | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/server/accounts.go, modules/backend/internal/server/roles.go, modules/backend/internal/store/account_model.go, modules/backend/internal/store/role_policy.go, modules/backend/internal/authz/ | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | -| dev-superadmin-u4-ui-surface | modules/backend/internal/server/accounts.go, modules/frontend/src/components/AdminZone.tsx, modules/frontend/src/components/AccountUsersPanel.tsx, modules/frontend/src/components/adminSections.tsx, modules/frontend/e2e/admin-user-create.playwright.ts, modules/frontend/e2e/iam-role-authority.playwright.ts | AGENT-EXECUTION.md | implementation | cursor → agy → pi | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | NOT_RUN | — | +| dev-superadmin-u1-bootstrap | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/store/account_model.go, modules/backend/internal/store/migrate.go, modules/backend/internal/server/server.go, scripts/svc.sh | AGENT-EXECUTION.md | implementation | cursor → agy → pi | dffc8e4ac3b0 | cursor / cursor-agent-stable | success | 484b7fdf2a3df449acf0143cdabf5480e563fb51 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u1-bootstrap-c02cd0aa.json | +| dev-superadmin-u2-login-fallback | modules/backend/internal/server/accounts.go, modules/backend/internal/store/auth.go, modules/backend/internal/server/auth.go, modules/backend/internal/server/login_recovery_test.go | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 91b105b7880c | cursor / cursor-agent-stable | success | c5dcb84a42160bb173ef09527480c7e678aa5af4 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u2-login-fallback-2eb00297.json | +| dev-superadmin-u3-privilege-protection | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/server/accounts.go, modules/backend/internal/server/roles.go, modules/backend/internal/store/account_model.go, modules/backend/internal/store/role_policy.go, modules/backend/internal/authz/ | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 2261db6dd595 | cursor / cursor-agent-stable | success | 69177feb3ba566f7d8cdffe92aeaeae143d00789 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u3-privilege-protection-e2fe8c1e.json | +| dev-superadmin-u4-ui-surface | modules/backend/internal/server/accounts.go, modules/frontend/src/components/AdminZone.tsx, modules/frontend/src/components/AccountUsersPanel.tsx, modules/frontend/src/components/adminSections.tsx, modules/frontend/e2e/admin-user-create.playwright.ts, modules/frontend/e2e/iam-role-authority.playwright.ts | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 7f9287b28660 | cursor / cursor-agent-stable | success | e6bb387f715b0700bf094ef9ce660eea458c7d5d | none | /home/weichen/.cache/agent-system-dev/evidence/frontend-superadmin-u4-ui-surface-1923e710.json | ## 关联方向与规划 From 786c2849cb4b736603de7b73acaa017b1eceb82a Mon Sep 17 00:00:00 2001 From: agent-exec-transport Date: Mon, 19 Oct 2026 03:39:22 +0000 Subject: [PATCH 05/13] agent-exec transport 5cd470726de043381170b777d3eda39f/90b4ae249497 --- modules/backend | 2 +- modules/frontend | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/modules/backend b/modules/backend index 646dc576..69177feb 160000 --- a/modules/backend +++ b/modules/backend @@ -1 +1 @@ -Subproject commit 646dc57673c972fb8041ca06e52e803576f5005d +Subproject commit 69177feb3ba566f7d8cdffe92aeaeae143d00789 diff --git a/modules/frontend b/modules/frontend index 1650b4ff..23877af9 160000 --- a/modules/frontend +++ b/modules/frontend @@ -1 +1 @@ -Subproject commit 1650b4fff0163e48a752ecbd86a3c4b18771e287 +Subproject commit 23877af9607b842d0b1dbb9e35d719ec64e696d9 From 66cbc40b31fd0d31a5c75bffc170fc4e886fb367 Mon Sep 17 00:00:00 2001 From: agent-exec-transport Date: Mon, 19 Oct 2026 03:57:10 +0000 Subject: [PATCH 06/13] agent-exec transport 513d7fdc9b57f65bfc820b7e8e5e37b4/5cd6822918e8 --- modules/frontend | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/modules/frontend b/modules/frontend index 23877af9..9df5517e 160000 --- a/modules/frontend +++ b/modules/frontend @@ -1 +1 @@ -Subproject commit 23877af9607b842d0b1dbb9e35d719ec64e696d9 +Subproject commit 9df5517e9ceb4934fcf4f649f9894f95661e3e69 From bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 03:59:09 +0000 Subject: [PATCH 07/13] Record the sync checkpoint Why: bind the task validation checkpoint to the integration baseline. Evidence: SELF recursive component checks; sync_base=7716b28cfff5200e7cfe9ec75aff5bcd71b234ed; before_record=ebcdaf155b5a25c68ac7cba6b00d8d61428561b5. Impact: task metadata only. Refs: .task/feature-super-admin.md --- .task/feature-super-admin.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md index 664c27e1..e41ccd48 100644 --- a/.task/feature-super-admin.md +++ b/.task/feature-super-admin.md @@ -171,3 +171,4 @@ "receipt_path": "/home/weichen/.cache/agent-system-dev/evidence/c657e9c3dd3c1b526ad5b5a50c0616d534812d3a753c436db4daefaa23b55446.json" } ``` +| 同步(记录前对象) | 7716b28cfff5200e7cfe9ec75aff5bcd71b234ed | ebcdaf155b5a25c68ac7cba6b00d8d61428561b5 | 2026-10-19T03:59:09Z | From 51d48bc6d1dda6d5e850135221f154e4b72546e5 Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 04:29:39 +0000 Subject: [PATCH 08/13] Record verification results and evidence in task card Why: Record author verifications, test results, and evidence receipts in the task card. Evidence: All 3 receipts (precheck, task-sync, make test) verified with exit 0. Impact: Task card metadata update only. Refs: #627 --- .task/feature-super-admin.md | 167 +++++++++++++++++++++++++++++++---- 1 file changed, 150 insertions(+), 17 deletions(-) diff --git a/.task/feature-super-admin.md b/.task/feature-super-admin.md index e41ccd48..de09b7cb 100644 --- a/.task/feature-super-admin.md +++ b/.task/feature-super-admin.md @@ -92,6 +92,7 @@ | 节点 | sync_base_sha | tested_head_sha | checked_at | |---|---|---|---| | 启动 | d9ac28f89159e17781e2a8ef3094965130f29d2f | d9ac28f89159e17781e2a8ef3094965130f29d2f | 2026-10-19T01:39:50Z | +| 验收前同步 | 7716b28cfff5200e7cfe9ec75aff5bcd71b234ed | bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc | 2026-10-19T04:04:39Z | ## 证据(Evidence) @@ -101,35 +102,51 @@ ## 交付调度 -- 调度状态:未入队;调度记录:无 -- entry_id:无;attempt_id:无;窗口执行者:无 -- 固定候选:无(base/head、组件与相关配置引用实际尝试) +- 调度状态:待合入;调度记录:PR #627 +- entry_id:627;attempt_id:bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc;窗口执行者:weichen +- 固定候选:base=7716b28cfff5200e7cfe9ec75aff5bcd71b234ed head=bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc - 调度依据:policy/delivery.md#合入调度 -- 固定后证据:源码外 RECEIPT;实际结果后按授权原样导入和闭合 +- 固定后证据:源码外 RECEIPT(precheck 6b88d5de, task-sync 6fb97d54, test 03eba6c3);实际结果后按授权原样导入和闭合 ## 结果与验证(完成后填写) - 结果: -- 验证:<结论摘要 PASS/FAIL/SKIP/NOT_RUN 逐项;逐条证据由 make evidence 写入上方证据表> + - R1:超级管理员独立身份与凭据分离:通过 `.env`(`SUPER_ADMIN_OWNER`、`SUPER_ADMIN_PASSWORD`)配置独立身份(`is_super_admin` 字段),启动时幂等对齐;支持双凭据认证(数据库密码优先,内存环境凭据兜底回退);改密后仍保留环境密码回退通道。 + - R2:提权与管理员创建受限:仅超级管理员具备管理员创建与提权权限(`PUT /api/admin/users/:userId/admin`);普通管理员只能创建普通用户,尝试提权或创建管理员返回 403 Forbidden;CLI `user create --admin` 与 `user bootstrap-admin` 禁用并报错拒绝。 + - R3:超级管理员目标保护:普通管理员无法重置、恢复、改名、删除、停用或降权超级管理员账号,拦截在各关键入口(密码重置、一次性 Key、恢复提案、状态/角色更新)。 + - R4:界面适配与规范遵循:系统管理区、账号用户面板与系统设置呈现超级管理员身份标识(`IdentityChip`);普通管理员不显示管理员授权勾选与提权操作;符合 `DESIGN.md` 令牌规范。 +- 验证(SELF): + - `make test-boundaries`:PASS(架构与边界 102 条边校验通过)。 + - `make test-pins`:PASS(所有子模块与依赖 pin 校验通过)。 + - `make frontend`:PASS(前端 tsc 构建完成,静态资源同步至后端分发目录)。 + - `make build`:PASS(编译 `bin/agent-system` 与 `bin/storage-migrate` 通过)。 + - `make test-frontend`:PASS(49 个测试文件,574 项测试全部通过,knip 50/51 通过)。 + - `make test-backend`:PASS(全量后端测试通过)。 + - 全量 `make test ```json @@ -172,3 +189,119 @@ } ``` | 同步(记录前对象) | 7716b28cfff5200e7cfe9ec75aff5bcd71b234ed | ebcdaf155b5a25c68ac7cba6b00d8d61428561b5 | 2026-10-19T03:59:09Z | + + +```json +{ + "summary_schema": 1, + "source": "SELF", + "timestamp": "2026-10-19T04:02:36.248295+00:00", + "command": "make precheck", + "exit_code": 0, + "cwd": "/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin", + "before_head": "bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc", + "after_head": "bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc", + "branch": "feature/super-admin", + "target_branch": "main", + "target_head": "7716b28cfff5200e7cfe9ec75aff5bcd71b234ed", + "root_target": "main", + "immediate_target": "main", + "before_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "after_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "output_tail": [ + "make[1]: Entering directory '/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin'", + "[repo] branch=feature/super-admin head=bf190d6e09", + "[remote] origin/main=7716b28cff ahead=8 behind=0", + "[tree] clean submodules_drift=0 uninit=0", + "[worktrees] linked=6", + "[recycle] merged un-recycled branches: feature/layered-python-env", + "[initiatives] local cards (not authoritative): none", + "[hooks] core.hooksPath=scripts/hooks(pre-commit/post-merge 实际接线)", + "[facts] policy/facts.md 6 条事实均在有效期内", + "[required-reading] core/baseline.md, workflows/delivery.md §1, policy/delivery.md", + "[R0] 7716b28cff(完整:7716b28cfff5200e7cfe9ec75aff5bcd71b234ed)", + "[worktree] before-sync: recursive component checks passed", + "[verdict] READY — 保留本次 precheck receipt 后建任务工作区:PRECHECK_RECEIPT=/tmp/task-precheck.json make task-start NAME=feature/your-branch", + "make[1]: Leaving directory '/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin'" + ], + "output_sha256": "e399416a72ef0614e5b58b618b6683e38cdfb63ef9a92c6dda9e0d6d1690f77a", + "receipt_sha256": "6b88d5def06a9fb6b89579b3fcef401742773620b08e8e9563c5d75af5603183", + "receipt_path": "/home/weichen/.cache/agent-system-dev/evidence/6b88d5def06a9fb6b89579b3fcef401742773620b08e8e9563c5d75af5603183.json" +} +``` + + +```json +{ + "summary_schema": 1, + "source": "SELF", + "timestamp": "2026-10-19T04:04:00.556658+00:00", + "command": "make task-sync", + "exit_code": 0, + "cwd": "/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin", + "before_head": "bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc", + "after_head": "bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc", + "branch": "feature/super-admin", + "target_branch": "main", + "target_head": "7716b28cfff5200e7cfe9ec75aff5bcd71b234ed", + "root_target": "main", + "immediate_target": "main", + "before_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "after_tracked_diff_sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "output_tail": [ + "make[1]: Entering directory '/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin'", + "[worktree] before-sync: recursive component checks passed", + "[worktree] before-update: recursive component checks passed", + "[worktree] materialize: recursive component checks passed", + "[worktree] after-sync: recursive component checks passed", + "[evidence] WARN JSON receipt line 135: unverified: recorded component state was not at its pinned SHA ——关键检查须重跑并以 make evidence 重新写入", + "[synced] sync_base=7716b28cfff5200e7cfe9ec75aff5bcd71b234ed tested_head=bf190d6e09ee32c9e1c57ac3a5a601c0f71f48bc checked_at=2026-10-19T04:04:39Z changed=0 sync_target=main", + "[next] 跑正式验收(make test 等),证据写入任务卡", + "make[1]: Leaving directory '/home/weichen/projects/Agent-System-Dev-wt-feature-super-admin'" + ], + "output_sha256": "c124911fc3bf775412911304fd1e977ad38d899c6745d47a51bc719628331183", + "receipt_sha256": "6fb97d54760af478b74818c09526c83259eaef880b07ab22ac93d5a5f36861e7", + "receipt_path": "/home/weichen/.cache/agent-system-dev/evidence/6fb97d54760af478b74818c09526c83259eaef880b07ab22ac93d5a5f36861e7.json" +} +``` + + +```json +{ + "summary_schema": 1, + "source": "SELF", + "timestamp": "2026-10-19T04:20:16.115006+00:00", + "command": "umask 022 && make test Date: Mon, 19 Oct 2026 04:30:01 +0000 Subject: [PATCH 09/13] Fold-close the task card before merge MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Why: close the task card inside its own PR so landing it needs no post-merge backfill or separate close PR. Evidence: .task/feature-super-admin.md -> .task/archive/feature-super-admin.md; status 已完成(合入前闭合); PR #627 https://git-home.u1680832.nyat.app:30319/weichen/Agent-System-Dev/pulls/627. Impact: task metadata only; the card is archived within PR #627 and lands with its merge commit. Refs: task.sh close --self --- .task/{ => archive}/feature-super-admin.md | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) rename .task/{ => archive}/feature-super-admin.md (98%) diff --git a/.task/feature-super-admin.md b/.task/archive/feature-super-admin.md similarity index 98% rename from .task/feature-super-admin.md rename to .task/archive/feature-super-admin.md index de09b7cb..4587cfb5 100644 --- a/.task/feature-super-admin.md +++ b/.task/archive/feature-super-admin.md @@ -1,6 +1,6 @@ # feature/super-admin 任务卡 -任务主记录:PR #627 https://git-home.u1680832.nyat.app:30319/weichen/Agent-System-Dev/pulls/627;状态:进行中;owner:weichen +任务主记录:PR #627 https://git-home.u1680832.nyat.app:30319/weichen/Agent-System-Dev/pulls/627;状态:已完成(合入前闭合);owner:weichen ## 基线与授权 @@ -108,7 +108,7 @@ - 调度依据:policy/delivery.md#合入调度 - 固定后证据:源码外 RECEIPT(precheck 6b88d5de, task-sync 6fb97d54, test 03eba6c3);实际结果后按授权原样导入和闭合 -## 结果与验证(完成后填写) +## 结果与验证 - 结果: - R1:超级管理员独立身份与凭据分离:通过 `.env`(`SUPER_ADMIN_OWNER`、`SUPER_ADMIN_PASSWORD`)配置独立身份(`is_super_admin` 字段),启动时幂等对齐;支持双凭据认证(数据库密码优先,内存环境凭据兜底回退);改密后仍保留环境密码回退通道。 @@ -305,3 +305,9 @@ "receipt_path": "/home/weichen/.cache/agent-system-dev/evidence/03eba6c34f14ca083f8c14c3aa20c0e294d74690fb7c2490cedcb4dbc1514f83.json" } ``` + +## 闭合记录(合入前折叠) + +- 本卡在 PR #627(https://git-home.u1680832.nyat.app:30319/weichen/Agent-System-Dev/pulls/627)合入前闭合并归档,随该 PR 一同合入。 +- 该 PR 的合并提交即本任务的落地记录。 +- 合入后无需回填,也无需单独的闭合 PR。 From a731ef54a354f797dbc8aa5e7012dad2eb389cb6 Mon Sep 17 00:00:00 2001 From: agent-exec-transport Date: Mon, 19 Oct 2026 04:46:49 +0000 Subject: [PATCH 10/13] agent-exec transport 51708f296381a61509ea5f53aa51269b/b4647884f68f --- scripts/svc.sh | 6 ++++++ tests/integration/lifecycle/test_lifecycle_real.py | 4 +++- tests/test_svc_realcombo.py | 4 +++- 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/scripts/svc.sh b/scripts/svc.sh index d8d1ab66..9993537a 100755 --- a/scripts/svc.sh +++ b/scripts/svc.sh @@ -1534,6 +1534,12 @@ svc_launch_serve() { if [ -n "${RDM_DISABLE_EXEC_TOOLS:-}" ]; then args+=("RDM_DISABLE_EXEC_TOOLS=$RDM_DISABLE_EXEC_TOOLS") fi + # 超级管理员凭据只从本次环境转发,不写入 serve.env;缺失时由 serve 自行 fail closed。 + for k in SUPER_ADMIN_OWNER SUPER_ADMIN_PASSWORD AGENT_SYSTEM_ENV_FILE; do + if [ -n "${!k+x}" ]; then + args+=("$k=${!k}") + fi + done # shellcheck disable=SC2086 nohup "${args[@]}" "$ENV_BIN" serve $exec_args >> "$ENV_DIR/svc.log" 2>&1 9>&- & } diff --git a/tests/integration/lifecycle/test_lifecycle_real.py b/tests/integration/lifecycle/test_lifecycle_real.py index d0569726..c9902eb6 100644 --- a/tests/integration/lifecycle/test_lifecycle_real.py +++ b/tests/integration/lifecycle/test_lifecycle_real.py @@ -86,6 +86,8 @@ class LifecycleRealTests(tsr.SvcAutoRecoverTests): def initialize_store(self, data, env=None): init_env = dict(self.env if env is None else env) init_env["RDM_DISABLE_EXEC_TOOLS"] = "1" + init_env.setdefault("SUPER_ADMIN_OWNER", "superadmin") + init_env.setdefault("SUPER_ADMIN_PASSWORD", "realcombo-super-admin-password") if env is None: init_env.pop("AGENT_SYSTEM_DSN", None) with socket.socket() as sock: @@ -95,7 +97,7 @@ class LifecycleRealTests(tsr.SvcAutoRecoverTests): with log_path.open("wb") as log: proc = subprocess.Popen( [str(self.real_bin), "serve", "--addr", "127.0.0.1:%d" % port, - "--data", str(data), "--auth", "on"], + "--data", str(data), "--auth", "auto"], cwd=self.root, env=init_env, stdout=log, stderr=log) try: for _ in range(200): diff --git a/tests/test_svc_realcombo.py b/tests/test_svc_realcombo.py index ea1971d0..2eaf13c4 100644 --- a/tests/test_svc_realcombo.py +++ b/tests/test_svc_realcombo.py @@ -121,6 +121,8 @@ class RealComboTests(tsr.SvcAutoRecoverTests): """ init_env = dict(self.env if env is None else env) init_env["RDM_DISABLE_EXEC_TOOLS"] = "1" + init_env.setdefault("SUPER_ADMIN_OWNER", "superadmin") + init_env.setdefault("SUPER_ADMIN_PASSWORD", "realcombo-super-admin-password") if env is None: init_env.pop("AGENT_SYSTEM_DSN", None) with socket.socket() as sock: @@ -130,7 +132,7 @@ class RealComboTests(tsr.SvcAutoRecoverTests): with log_path.open("wb") as log: proc = subprocess.Popen( [str(binary), "serve", "--addr", "127.0.0.1:%d" % port, - "--data", str(data), "--auth", "on"], + "--data", str(data), "--auth", "auto"], cwd=self.root, env=init_env, stdout=log, stderr=log) try: for _ in range(200): From 0de0d2397ec83fb6b1ab32acaf4bb8f028f53326 Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 04:57:23 +0000 Subject: [PATCH 11/13] Record repair unit in archived task card Why: Record the dev-superadmin-repair-svc-realcombo repair unit that fixed the real combo test fixture and service environment forwarding. Evidence: Receipts in /home/weichen/.cache/agent-system-dev/evidence/dev-superadmin-repair-svc-realcombo.json; tests pass. Impact: Task card metadata updated. Refs: PR #627 --- .task/archive/feature-super-admin.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.task/archive/feature-super-admin.md b/.task/archive/feature-super-admin.md index 4587cfb5..340dc10b 100644 --- a/.task/archive/feature-super-admin.md +++ b/.task/archive/feature-super-admin.md @@ -40,6 +40,7 @@ | dev-superadmin-u2-login-fallback | modules/backend/internal/server/accounts.go, modules/backend/internal/store/auth.go, modules/backend/internal/server/auth.go, modules/backend/internal/server/login_recovery_test.go | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 91b105b7880c | cursor / cursor-agent-stable | success | c5dcb84a42160bb173ef09527480c7e678aa5af4 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u2-login-fallback-2eb00297.json | | dev-superadmin-u3-privilege-protection | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/server/accounts.go, modules/backend/internal/server/roles.go, modules/backend/internal/store/account_model.go, modules/backend/internal/store/role_policy.go, modules/backend/internal/authz/ | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 2261db6dd595 | cursor / cursor-agent-stable | success | 69177feb3ba566f7d8cdffe92aeaeae143d00789 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u3-privilege-protection-e2fe8c1e.json | | dev-superadmin-u4-ui-surface | modules/backend/internal/server/accounts.go, modules/frontend/src/components/AdminZone.tsx, modules/frontend/src/components/AccountUsersPanel.tsx, modules/frontend/src/components/adminSections.tsx, modules/frontend/e2e/admin-user-create.playwright.ts, modules/frontend/e2e/iam-role-authority.playwright.ts | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 7f9287b28660 | cursor / cursor-agent-stable | success | e6bb387f715b0700bf094ef9ce660eea458c7d5d | none | /home/weichen/.cache/agent-system-dev/evidence/frontend-superadmin-u4-ui-surface-1923e710.json | +| dev-superadmin-repair-svc-realcombo | tests/test_svc_realcombo.py, tests/integration/lifecycle/test_lifecycle_real.py, scripts/svc.sh | AGENT-EXECUTION.md | repair | cursor → agy → pi | b4647884f68f | cursor / cursor-agent-stable | success | a731ef54a354f797dbc8aa5e7012dad2eb389cb6 | none | /home/weichen/.cache/agent-system-dev/evidence/dev-superadmin-repair-svc-realcombo.json | ## 关联方向与规划 From 37c619ecc7933896224e060d13a529c90b95e3a0 Mon Sep 17 00:00:00 2001 From: agent-exec-transport Date: Mon, 19 Oct 2026 05:36:09 +0000 Subject: [PATCH 12/13] agent-exec transport a6410084d06dab307808de69b1d29c7c/25fde07da168 --- .../multi-instance/multi_instance_test.go | 38 +++++-------------- tests/load/collaboration/run_load.sh | 4 +- tests/test_svc.py | 2 +- 3 files changed, 13 insertions(+), 31 deletions(-) diff --git a/tests/integration/multi-instance/multi_instance_test.go b/tests/integration/multi-instance/multi_instance_test.go index 1a4ede06..95370efc 100644 --- a/tests/integration/multi-instance/multi_instance_test.go +++ b/tests/integration/multi-instance/multi_instance_test.go @@ -345,7 +345,10 @@ func (e *env) startInstance(t *testing.T, name, addr string) *instance { cmd.Stdout, cmd.Stderr = log, log // 演练环境可能带有空的对象存储变量。子进程必须按「未配置」启动, // 否则测不到带类型空 *S3 回落本地目录的路径。 - cmd.Env = withoutBlobstoreS3(os.Environ()) + cmd.Env = append(withoutBlobstoreS3(os.Environ()), + "SUPER_ADMIN_OWNER=mi-root", + "SUPER_ADMIN_PASSWORD=MiRootPass12345!", + ) // 独立 cwd:serve 会向 ./data 写 skills/SQLite 等,不能落在测试目录。 dataDir := t.TempDir() cmd.Dir = dataDir @@ -455,10 +458,8 @@ func (e *env) killNine(t *testing.T, inst *instance) { // 独占落 JSON),redeem 会话进入 grant-setup 改密设 alicePass,完成后再发 Key。 func (e *env) loginAlice(t *testing.T) *userClient { t.Helper() - // 空库先引导首个管理员(本地 pending 创建要求库内已有用户),再建 alice。 - // 两步都签发一次性凭据,独占落临时 JSON;mi-root 的凭据随后用于初始化其账号。 - rootCred := filepath.Join(t.TempDir(), "root-cred.json") - e.cliIn(t, e.a.dataDir, "user", "bootstrap-admin", "--dsn", e.dbDSN, "--owner", "mi-root", "--out-file", rootCred) + // 超级管理员 mi-root 已由 serve 启动时的 SUPER_ADMIN_* 建立;这里只建 alice, + // 一次性激活凭据独占落临时 JSON。 activation := filepath.Join(t.TempDir(), "activation.json") e.cliIn(t, e.a.dataDir, "user", "create", "--dsn", e.dbDSN, "--owner", aliceOwner, "--name", "Alice", "--out", activation) activateKey := activationSecret(t, activation) @@ -477,7 +478,7 @@ func (e *env) loginAlice(t *testing.T) *userClient { apiKey := e.cliOut(t, "apikey", "create", "--dsn", e.dbDSN, "--owner", aliceOwner, "--name", "mi-acceptance") // IAM U4 把建项目改为系统动作 project.create:由引导管理员经真实 API 授予 alice。 - e.grantAliceProjectCreate(t, rootCred) + e.grantAliceProjectCreate(t) uc := &userClient{ api: &http.Client{Timeout: httpWait, Transport: bearerRT{key: apiKey}}, apiB: &http.Client{Timeout: httpWait, Transport: bearerRT{key: apiKey}}, @@ -491,30 +492,9 @@ func (e *env) loginAlice(t *testing.T) *userClient { // grantAliceProjectCreate 以 mi-root 身份经 admin API 为 alice 追加系统授权 // project.create(保留其已有授权;PUT 为整体替换,按 authorityEpoch 乐观并发)。 -// bootstrap-admin 只签发一次性凭据,mi-root 未初始化前不能发 API key,故先照 -// alice 的方式 redeem 并设 rootPass。 -func (e *env) grantAliceProjectCreate(t *testing.T, rootCred string) { +// mi-root 由 serve 启动时的 SUPER_ADMIN_* 建立,可直接为其发 API key。 +func (e *env) grantAliceProjectCreate(t *testing.T) { t.Helper() - raw, err := os.ReadFile(rootCred) - if err != nil { - t.Fatal(err) - } - rootSecret := strings.TrimSpace(string(raw)) - if rootSecret == "" { - t.Fatal("bootstrap-admin credential file is empty") - } - jar, err := cookiejar.New(nil) - if err != nil { - t.Fatal(err) - } - sess := &http.Client{Timeout: httpWait, Jar: jar} - e.do(t, sess, "POST", "/api/auth/login-key/redeem", map[string]any{ - "key": rootSecret, - }, nil) - e.do(t, sess, "POST", "/api/auth/password", map[string]any{ - "next": rootPass, - }, nil) - rootKey := e.cliOut(t, "apikey", "create", "--dsn", e.dbDSN, "--owner", "mi-root", "--name", "mi-acceptance-root") root := &http.Client{Timeout: httpWait, Transport: bearerRT{key: rootKey}} var users []struct { diff --git a/tests/load/collaboration/run_load.sh b/tests/load/collaboration/run_load.sh index a62c0834..93c561a6 100755 --- a/tests/load/collaboration/run_load.sh +++ b/tests/load/collaboration/run_load.sh @@ -117,7 +117,9 @@ u = urlsplit(sys.argv[1]) print(urlunsplit((u.scheme, u.netloc, "/u7load_app", u.query, ""))) PY )" -"$BIN" user create --dsn "$APP_DSN" --admin --owner load_admin --password load-admin-pass-Aa1 >/dev/null +# load_admin 由 serve 启动时按 SUPER_ADMIN_* 建立为超级管理员。 +export SUPER_ADMIN_OWNER=load_admin +export SUPER_ADMIN_PASSWORD=load-admin-pass-Aa1 "$BIN" user create --dsn "$APP_DSN" --owner probe_user --password probe-user-pass-Aa9 >/dev/null # ---- 3b) B5 seed(可选):先建 seed_u* 再 COPY 灌量 ---- diff --git a/tests/test_svc.py b/tests/test_svc.py index 60ebf1cb..b1a64636 100644 --- a/tests/test_svc.py +++ b/tests/test_svc.py @@ -893,7 +893,7 @@ class SvcDbRecoveryTests(unittest.TestCase): def test_rdm_source_deploy_end_to_end(self): remote, work = self.make_rdm_repo() env = self.rdm_env(remote) - result = self.svc("rdm1", "deploy", "--from", "rdm", "--port", "18841", env=env) + result = self.svc("rdm1", "deploy", "--from", "rdm", "--port", "18843", env=env) d = self.runtime("rdm1") # U2:组合产物入不可变 release,经 current 指针解析;插件空集、工作台随 release。 active = d / "current" From d500a2e4fc8d9844ebff63b0531c67f5a9536eb8 Mon Sep 17 00:00:00 2001 From: weichen Date: Mon, 19 Oct 2026 05:37:34 +0000 Subject: [PATCH 13/13] Record multi-instance repair unit in archived task card Why: Record the dev-superadmin-repair-multi-instance repair unit that fixed the multi-instance tests, test_svc port, and load test scripts for super-admin credentials. Evidence: Receipts in /home/weichen/.cache/agent-system-dev/evidence/dev-superadmin-repair-multi-instance.json; make test-multi-instance passes (15.753s). Impact: Task card metadata updated. Refs: PR #627 --- .task/archive/feature-super-admin.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.task/archive/feature-super-admin.md b/.task/archive/feature-super-admin.md index 340dc10b..d895b93c 100644 --- a/.task/archive/feature-super-admin.md +++ b/.task/archive/feature-super-admin.md @@ -41,6 +41,7 @@ | dev-superadmin-u3-privilege-protection | modules/backend/cmd/agent-system/main.go, modules/backend/internal/app/, modules/backend/internal/server/accounts.go, modules/backend/internal/server/roles.go, modules/backend/internal/store/account_model.go, modules/backend/internal/store/role_policy.go, modules/backend/internal/authz/ | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 2261db6dd595 | cursor / cursor-agent-stable | success | 69177feb3ba566f7d8cdffe92aeaeae143d00789 | none | /home/weichen/.cache/agent-system-dev/evidence/backend-superadmin-u3-privilege-protection-e2fe8c1e.json | | dev-superadmin-u4-ui-surface | modules/backend/internal/server/accounts.go, modules/frontend/src/components/AdminZone.tsx, modules/frontend/src/components/AccountUsersPanel.tsx, modules/frontend/src/components/adminSections.tsx, modules/frontend/e2e/admin-user-create.playwright.ts, modules/frontend/e2e/iam-role-authority.playwright.ts | AGENT-EXECUTION.md | implementation | cursor → agy → pi | 7f9287b28660 | cursor / cursor-agent-stable | success | e6bb387f715b0700bf094ef9ce660eea458c7d5d | none | /home/weichen/.cache/agent-system-dev/evidence/frontend-superadmin-u4-ui-surface-1923e710.json | | dev-superadmin-repair-svc-realcombo | tests/test_svc_realcombo.py, tests/integration/lifecycle/test_lifecycle_real.py, scripts/svc.sh | AGENT-EXECUTION.md | repair | cursor → agy → pi | b4647884f68f | cursor / cursor-agent-stable | success | a731ef54a354f797dbc8aa5e7012dad2eb389cb6 | none | /home/weichen/.cache/agent-system-dev/evidence/dev-superadmin-repair-svc-realcombo.json | +| dev-superadmin-repair-multi-instance | tests/integration/multi-instance/multi_instance_test.go, tests/test_svc.py, tests/load/collaboration/run_load.sh | AGENT-EXECUTION.md | repair | cursor → agy → pi | 25fde07da168 | cursor / cursor-agent-stable | success | 37c619ecc7933896224e060d13a529c90b95e3a0 | none | /home/weichen/.cache/agent-system-dev/evidence/dev-superadmin-repair-multi-instance.json | ## 关联方向与规划