docs: refine mdtodo web operable spec

This commit is contained in:
Codex
2026-06-26 11:33:33 +00:00
parent 4c9343a226
commit aeaa38c663
@@ -19,7 +19,7 @@
| 短名 | 项目管理 |
| 层级 | L2 课题 |
| 状态 | 已生效 |
| 实现引用版本 | draft-2026-06-25-p0-project-management-mdtodo; draft-2026-06-25-p0-mdtodo-web-active-editing-hwpod-source |
| 实现引用版本 | draft-2026-06-25-p0-project-management-mdtodo; draft-2026-06-25-p0-mdtodo-web-active-editing-hwpod-source; draft-2026-06-26-p1-mdtodo-web-operable |
| 需求规格模板 | [ISO/IEC/IEEE 29148 需求规格模板](../../templates/iso-iec-ieee-29148-requirements-spec-template.md) |
| 上级规格 | [PJ2026-0104 客户端](PJ2026-0104-client.md) |
| 关联规格 | [PJ2026-010401 Web工作台](PJ2026-010401-web-workbench.md)、[PJ2026-010403 API契约](PJ2026-010403-api-contract.md)、[PJ2026-0102 Agent编排](PJ2026-0102-agent-orchestration.md)、[PJ2026-0105 用户管理](PJ2026-0105-user-management.md)、[PJ2026-0106 平台运维](PJ2026-0106-platform-ops.md) |
@@ -37,6 +37,8 @@
`/projects/mdtodo` 的目标交互不只是只读投影。页面应支持 Web 配置 MDTODO Source、绑定 HWPOD workspace、按 Rxx 标准展示任务树、执行任务编辑 mutation,并通过受控 web-probe command 做交互式验收。Source/File 选择应收敛为顶部状态栏下拉,统计/诊断信息应进入 info/diagnostic 弹窗,主版面优先分配给任务树和编辑区。
`draft-2026-06-26-p1-mdtodo-web-operable` 的目标是把 MDTODO Web 从只读摘要收敛为可工作的任务面:File 下拉主标签必须是 `docs/MDTODO/` 下直接 Markdown 文件名;任务详情必须展示正文 Markdown 和可解析报告链接;报告链接必须在右侧预览并支持全屏;标题和正文编辑必须通过双击/inline editing 进入;Workbench launch 必须生成带任务上下文的首轮可执行内容,不能只创建空 session。
项目管理从 P0 起必须作为独立 `hwlab-project-management` 微服务交付。它不作为 `hwlab-cloud-api` 内部模块起步,也不并入既有 UniDesk `mdtodo`、UniDesk `project-manager`、HWLAB Workbench runtime、Cloud Web 或 user-billing 服务。
### 2.2 范围内
@@ -44,6 +46,7 @@
- Cloud Web `/projects` 根导航、项目列表、source 状态、能力摘要、blocker 和最近 Workbench link 展示。
- Cloud Web `/projects/mdtodo` 页面,展示 MDTODO source、Markdown 文件摘要、任务树、任务详情、状态、稳定 `taskRef`、链接摘要和 Workbench 启动入口。
- `/projects/mdtodo` 的 Source 配置弹窗、HWPOD source binding、Source/File 顶部下拉、metric info/diagnostic 弹窗、Rxx 任务树和主动编辑控件。
- `/projects/mdtodo` 的任务详情正文、Markdown report link 解析、右侧报告预览、全屏预览和 inline edit 操作。
- 独立 `hwlab-project-management` 微服务,包括 Project Management API、ProjectSource registry、MDTODO adapter 调度、DB read model、Workbench link 表、audit/outbox 和未来外部 PM adapter 扩展点。
- MDTODO adapter 对 Markdown TODO 文件的 Rxx heading 解析、文件锁、原子写入、重建投影、revision/fingerprint 并发保护和 parse error 表达。
- HWPOD-bound MDTODO source 对 `d601-f103-v2` 这类 HWPOD workspace 的 `docs/MDTODO/` 受控读写。
@@ -72,12 +75,14 @@
| ProjectRecord | HWLAB 项目摘要,包含 `projectId`、标题、默认 source、可见性和更新时间。 |
| MDTODO source | 指向一个受控 Markdown TODO 根目录或仓库视图的 ProjectSource。 |
| HWPOD-bound MDTODO source | `sourceKind=hwpod-workspace` 的 ProjectSource,绑定 `hwpodId``nodeId` 和 workspace 相对根,例如 `docs/MDTODO/`。 |
| Direct MDTODO file | HWPOD-bound source 根目录 `docs/MDTODO/` 的直接 `.md` 子文件;子目录内报告、日志和任务报告只能作为链接 target,不得注册为 MDTODO 文件。 |
| Rxx 任务树 | MDTODO 标准的 heading 任务树,使用 `R1``R1.1``R1.1.1` 等 id 表达父子关系,层级来自 Rxx id 前缀而不是 checkbox 缩进或 Markdown heading 数量。 |
| Markdown source-of-truth | MDTODO 的权威任务内容仍保存在 `.md` 文件中;DB 只保存可重建投影、link、audit/outbox。 |
| Document revision | 项目管理服务对单个 Markdown 文件内容、mtime、fingerprint 和 projection revision 的并发控制摘要。 |
| `taskRef` | 项目管理 API 返回的 opaque 任务引用,例如 `mdtodo:<sourceId>:<fileHash>#<taskId>`;只有项目管理服务和 adapter 能反解。 |
| ProjectTask | 从 source 投影出的任务 DTO,包含 `taskRef``projectId``sourceId`、title、status、父子关系、depth、linkCount 和更新时间。 |
| WorkbenchLaunchContext | 项目管理页面发给公共 Workbench Launch API 的脱敏上下文,包含 `sourceKind=project-management``projectId``taskRef`、title 摘要和 prompt template 标识。 |
| ReportPreview | 项目管理服务按 taskRef 和任务内 Markdown link 解析出的只读报告预览 DTO,包含链接标签、相对路径、内容摘要、Markdown 正文、fingerprint、mtime、大小限制诊断和全屏展示所需 metadata。 |
| ProjectWorkbenchLink | `projectId/taskRef/sessionId/traceId` 的稳定关联记录,用于从任务回到 Workbench session 或从 Workbench 元数据看到来源。 |
| PM DB 投影 | 项目管理服务维护的 `project_sources``mdtodo_documents``mdtodo_task_projection``project_workbench_links``project_audit_events` 等可重建表。 |
| Cloud API route/auth bridge | Cloud API 中只负责同源路由、AuthPrincipal、错误 envelope 和转发的桥接层;不拥有项目管理持久化或 Markdown 解析。 |
@@ -173,7 +178,9 @@ flowchart TD
Rxx --> Task[MdtodoTaskProjection]
Task --> Api[GET /v1/project-management/mdtodo/tasks]
Api --> UI[/projects/mdtodo task tree]
UI --> Intent[WorkbenchLaunchContext]
UI --> Detail[GET task detail with body + links]
Detail --> Preview[GET report preview]
UI --> Intent[WorkbenchLaunchContext + initial task prompt]
Intent --> Launch[POST /v1/workbench/launches]
Launch --> Sess[Workbench sessionId]
Sess --> Link[ProjectWorkbenchLink]
@@ -297,12 +304,16 @@ flowchart TD
页面布局应把 Source 和 File 选择压缩到顶部状态栏的两个下拉菜单;Source 配置由弹窗承载;Source/Files/Tasks/Links 等 metric 摘要进入 info/diagnostic 弹窗,不作为常驻大卡片占用主版面。任务树和详情/编辑区是主工作面,窄屏下也必须保持下拉、任务树、编辑控件和主要 action 可达且不重叠。
File 下拉主标签必须显示文件名或 source root 下的直接相对路径,例如 `20260609_频率判断_用户反馈.md`。Markdown 文档内部标题只能作为 secondary label、tooltip 或详情字段,不得覆盖文件名成为主选择值。文件列表必须只来自配置 root 的 direct `.md` children`details/**``*_Task_Report.md``*_log_*.md` 等报告文件只能作为任务链接 target,不得进入 File 下拉或 source 文件计数。
MDTODO 页面必须按 Rxx heading 标准组织任务树,至少支持 `R1``R1.1``R1.1.1` 的父子关系、展开/折叠、搜索、跳转、状态筛选和选中高亮。树 authority 来自项目管理 projection 中的 Rxx id 和 parentTaskRef,不得从 checkbox 缩进、DOM 缩进或标题级别临时推断。
MDTODO 页面不得把 source 级全量任务列表作为首屏依赖。首屏应读取 source 摘要、file 摘要和默认 selected file 或 selected subtree 的有界任务窗口;文件切换、展开 Rxx 分支、搜索和状态过滤再按 cursor/offset 或 parentTaskRef 请求后续窗口。对于 `constart-71freq-mdtodo` 这类大 source`/projects/mdtodo` 必须能在不下载全部任务投影的情况下识别 source、列出文件并进入可交互状态。
MDTODO 页面可以提供任务状态和内容写入入口,但写入必须进入项目管理服务,再由 MDTODO adapter 使用文件锁和原子写入修改 `.md`,随后重建投影。前端不得直接上传或覆盖 raw Markdown。主动操作范围至少包括标题/正文或 raw block 编辑、`open/in_progress/completed` 状态切换、添加根任务、添加子任务、延续 sibling、删除任务、保存文本块、刷新文件、reindex 和 Workbench launch。
任务详情必须在默认阅读态展示正文 Markdown、解析后的 report/task links、link target 存在性和最近更新时间。标题、正文和文本块修改必须采用双击进入 inline edit 的交互;独立常驻 Title input 或 Replace body textarea 只能作为诊断或过渡开发面,不得成为目标 UX。任务内 Markdown 报告链接点击后应在右侧预览栏渲染,支持全屏预览;渲染必须使用成熟 Markdown 渲染器并经过 HTML sanitization。
### 6.3 CLIENT-PM-REQ-003 独立项目管理微服务
| 编号 | 短名 | 主责模块 | 关联模块 |
@@ -327,12 +338,16 @@ MDTODO 的权威存储应保持为 `.md` 文件。项目管理 DB 只保存可
MDTODO adapter 应兼容 VSCode 插件的 Rxx heading 语义:任务标题以 `## R1``### R1.1``#### R1.1.1` 或等价 heading 起始;状态 marker 至少支持 `[completed]``[in_progress]` 和历史 `[Processing]``[Finished]` 的读侧兼容;parentTaskRef 来自 Rxx id 前缀。checkbox list parser 只能作为显式 legacy mode,不能和 Rxx 标准任务树混成同一个 authority。
HWPOD source discovery 必须按配置 root direct child 枚举 MDTODO 文件。递归发现、按文件内容猜测 `details/**` 报告、或把 task report 当作 document candidate 都属于错误文件范围。reindex 应清理旧投影中的 stale report documents,使 File count、File 下拉和 task projection 与 direct-file 规则一致。
PM DB 至少应能表达 `project_sources``mdtodo_documents``mdtodo_task_projection``project_workbench_links``project_audit_events` 或等价结构。`project_sources` 对 HWPOD source 保存 `sourceKind``hwpodId``nodeId`、workspace 相对根、能力开关和配置 revision;`mdtodo_documents` 记录 fileRef、fingerprint、mtime、lastIndexedAt、parseError 和 revision`mdtodo_task_projection` 记录 `taskRef`、rxxId、title、status、parentTaskRef、depth、linkCount、updatedAt 和 source fingerprintlink 表记录 `projectId/taskRef/sessionId/traceId`
任务投影读取 API 必须支持 fileRef、parentTaskRef、status/search 和 cursor/offset+limit 的受控窗口。服务端应对缺省 limit 使用 YAML 或代码常量声明的保守默认值,并对客户端传入 limit 套用最大上限;source 级全量导出只能作为显式管理/调试能力,不能作为普通 Web 页面、web-probe collect/analyze 或默认 CLI 输出的依赖。
所有写操作必须携带 expected document revision 或 fingerprint。revision 不匹配时返回 409/conflict 和脱敏诊断,不覆盖远端修改。删除任务必须明确影响范围,写入 audit,并在响应中返回新的 document revision 和 projection status。
任务详情 API 应返回 full task body、raw task block、parsed links、resolved report target metadata、fileRef、document fingerprint 和可写状态。报告预览 API 应按 taskRef 和 link id/path 读取同一 source root 内允许的报告文件,返回 Markdown 内容、fingerprint、mtime、byteCount 和 truncated/blocked 诊断;路径解析必须拒绝越权、绝对路径和 Secret 文件。
只有当多人实时协同编辑成为主需求、任务查询和权限规则复杂到 Markdown 投影无法支撑、外部 PM adapter 已经成为主写入源,并且具备可靠 Markdown export/import、审计、冲突解决和离线恢复方案时,才重新评估 DB 作为权威存储。
### 6.5 CLIENT-PM-REQ-005 Workbench Link 与解耦
@@ -347,6 +362,8 @@ Workbench 与项目管理必须互相解耦。项目管理页面不得 import `u
Workbench 可以保存和展示脱敏 `launchContext` 元数据,但 session、turn、message、trace 和 final response 的 authority 仍来自 Workbench durable projection。项目管理页面返回后通过 `GET /v1/project-management/workbench-links?taskRef=...` 读取 link 摘要,不从 Workbench 私有 store 反查。
MDTODO 发起的 Workbench launch 必须产生可观察的工作上下文。成功响应后的目标 session 至少应包含首轮用户消息、initial prompt、task context projection 或等价可执行 turn,使 `web-probe observe collect --view turn-summary` 能看到非空任务上下文;只创建空 session 并跳转属于 launch 失败。
### 6.6 CLIENT-PM-REQ-006 外部 PM adapter 边界
| 编号 | 短名 | 主责模块 | 关联模块 |
@@ -377,6 +394,8 @@ web-probe 必须提供 `observe collect --view project-mdtodo-summary` 或等价
项目管理 analyzer 应输出 `project-management-*``mdtodo-*``workbench-launch-*` 前缀 findings,避免在非 Workbench 页面误报 Workbench session/trace 专属 finding。
`draft-2026-06-26-p1-mdtodo-web-operable` 后,analyzer 还必须覆盖以下红/黄项:File 列表出现非 direct child `.md`File 下拉主 label 不是文件名;选中任务正文不可见;任务 report link 不可点击或预览为空;`launchWorkbenchFromMdtodo` 后 Workbench session `turns=0``MSG=0``TRACE=0`control/observer 的 source/file/task count 长时间分歧。上述 finding 的修复方向必须是 API/UI/launch 契约收敛,不是增大脚本超时或绕过页面访问内部服务。
### 6.8 CLIENT-PM-REQ-008 YAML-first 运行配置
| 编号 | 短名 | 主责模块 | 关联模块 |
@@ -406,5 +425,6 @@ Secret、DB DSN、provider token、session token、API key、host path 和 raw M
| P4 web-probe observe/analyze 项目管理支持 | [#2137](https://github.com/pikasTech/HWLAB/issues/2137) | observe/analyze 输出项目管理 page-kind evidencescript 仅为补证。 |
| P5 D601 YAML-first 部署与原入口验收 | [#2138](https://github.com/pikasTech/HWLAB/issues/2138) | D601/v03 selected origin 原入口通过 observe/analyze 完成 `/projects/mdtodo` 到 Workbench launch 验收。 |
| #2155 P0 增量 SPEC | [#2156](https://github.com/pikasTech/HWLAB/issues/2156) | HWPOD Source 配置、Rxx 主动编辑、web-probe command 验收和 D601 `docs/MDTODO/` 样例要求合并到 UniDesk master。 |
| #2206 P1 可工作 MDTODO Web | [#2206](https://github.com/pikasTech/HWLAB/issues/2206) | File 范围/标签、任务正文、报告预览、inline edit、Workbench 非空 launch 和 web-probe 红黄灯在 D601/v03 原入口收敛。 |
P0 SPEC 完成前不得进入项目管理代码实现。每个阶段独立 PR 跟踪;PR 合并后必须把 PR、commit、observe/analyze 报告或原入口证据回写到对应阶段 issue 和 [#2123](https://github.com/pikasTech/HWLAB/issues/2123)。