WARCH2 补强历史查询测试合同

这个提交包含在:
2026-05-20 08:06:31 +08:00
父节点 51c5af88b4
当前提交 7a32399ca9
@@ -1,7 +1,7 @@
"ID","Title","Description","Acceptance","Test_Method","Tools","Dev_Status","Review1_Status","Regression_Status","Files","Dependencies","Notes" "ID","Title","Description","Acceptance","Test_Method","Tools","Dev_Status","Review1_Status","Regression_Status","Files","Dependencies","Notes"
"WARCH2-0","只读查询合同与边界冻结","建立 WARCH2 企微审批历史只读查询 V1 合同;承接 WARCH1 已把请假/补卡历史写入 OA DB 并能离线读取,本阶段把 runner 级证明升级为正式 OA 可查能力。范围仅请假 + 补卡历史查询,不写企微、不创建模板、不提交审批、不开发外出/加班、不进入完整镜像、应急接管、恢复回写或 RuleOps。","1) 明确 WARCH2 是 WARCH1 后的正式查询切片;2) API 和页面均只读 OA DB,不调用企微 API;3) Secret 来源固定:WARCH2 查询自身不读取企微 Secret;若后续复用补偿读取,只能固定 WECOM_AGENT_SECRET,不尝试其他 Secret、无 fallback、不允许运行时猜 Secret;4) 不输出完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、表单原始 payload、附件或评论;5) 缺 OA 归档数据时输出空态或 PARTIAL_ARCHIVE_NEEDS_DATA,缺权限或外部配置时输出 NEEDS_CONFIG 或 SKIP/BLOCKED_BY_EXTERNAL_CONFIG,不伪造成镜像完成;6) 编码前给实现方案并获批。","受影响流程:企微主办请假/补卡 -> WARCH1 入库 -> OA 只读历史查询 -> 企微不可用时历史可查;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;人工批准实现方案后再编码。","python3|node|manual","TODO","TODO","TODO","issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv","[]","本行仅合同,无 schema、无业务代码、无部署副作用。回滚/清理:删除本合同前不得启动实现;实现阶段需独立记录回滚路径。" "WARCH2-0","只读查询合同与边界冻结","建立 WARCH2 企微审批历史只读查询 V1 合同;承接 WARCH1 已把请假/补卡历史写入 OA DB 并能离线读取,本阶段把 runner 级证明升级为正式 OA 可查能力。范围仅请假 + 补卡历史查询,不写企微、不创建模板、不提交审批、不开发外出/加班、不进入完整镜像、应急接管、恢复回写或 RuleOps。","1) 明确 WARCH2 是 WARCH1 后的正式查询切片;2) API 和页面均只读 OA DB,不调用企微 API;3) Secret 来源固定:WARCH2 查询自身不读取企微 Secret;若后续复用补偿读取,只能固定 WECOM_AGENT_SECRET,不尝试其他 Secret、无 fallback、不允许运行时猜 Secret;4) 不输出完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、表单原始 payload、附件或评论;5) 缺 OA 归档数据时输出空态或 PARTIAL_ARCHIVE_NEEDS_DATA,缺权限或外部配置时输出 NEEDS_CONFIG 或 SKIP/BLOCKED_BY_EXTERNAL_CONFIG,不伪造成镜像完成;6) 编码前给实现方案并获批。","受影响流程:企微主办请假/补卡 -> WARCH1 入库 -> OA 只读历史查询 -> 企微不可用时历史可查;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;人工批准实现方案后再编码。","python3|node|manual","TODO","TODO","TODO","issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv","[]","本行仅合同,无 schema、无业务代码、无部署副作用。回滚/清理:删除本合同前不得启动实现;实现阶段需独立记录回滚路径。"
"WARCH2-1","后端只读查询 API","新增企微审批历史只读 API,优先复用 WARCH1 归档服务,从 OA DB 查询请假/补卡历史列表、详情、参与人、动作、字段摘要和对账 finding;不调用企微 API。","1) 新增路由默认挂在 /api/wecom/approval-archive 或同等内部路径;2) 支持列表筛选:类型 leave/missed_punch、状态、时间范围、本人/管理范围、finding;3) 支持详情读取:状态、申请人/审批人脱敏摘要、字段摘要、动作历史、来源和 finding;4) 普通用户仅看本人作为申请人、参与人或动作处理人的记录;主管仅看直属下属申请和自己参与/操作过的记录,同部门非直属不可见;全量归档只允许 hr/admin/*;不得把 leave.view_all 或 attendance.view_all 单独解释为全量企微归档权限;5) callback-only、申请人未映射、参与人未映射或仅有外部 userid 的记录默认仅 hr/admin/* 可见;6) API 响应只返回脱敏外部键前缀和必要业务摘要。","受影响流程:OA 用户查看企微审批历史 -> 列表筛选 -> 查看详情 -> 对账 finding;验证步骤:cd server && node --check src/routes/wecomApprovalArchive.js;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;负例必须覆盖普通员工不可看他人记录、主管不能越过直属下属、同部门非直属不可见、finance/finance_mgr 仅有 attendance.view_all 或 leave.view_all 不得全量查看、详情 ID 猜测返回 403/404、scope=all 或 employeeId 过滤不能绕过权限、callback-only/未映射/仅外部 userid 只给 hr/admin/*。","node|vitest","TODO","TODO","TODO","server/src/routes/wecomApprovalArchive.js|server/src/services/integrations/wecomApprovalArchive.js|server/tests/unit/routes/wecomApprovalArchive.test.js","[""WARCH2-0""]","回滚路径:移除新增路由注册和测试;不删除 WARCH1 已入库历史证据。不得新增 Prisma migration,除非实现方案另行批准。权限实现必须按 OA employee_id 关联授权,不得用外部 userid、脱敏前缀、display_summary、department_id、leave.view_all 或 attendance.view_all 作为普通用户/主管授权依据。" "WARCH2-1","后端只读查询 API","新增企微审批历史只读 API,优先复用 WARCH1 归档服务,从 OA DB 查询请假/补卡历史列表、详情、参与人、动作、字段摘要和对账 finding;不调用企微 API。","1) 新增路由默认挂在 /api/wecom/approval-archive 或同等内部路径;2) 支持列表筛选:类型 leave/missed_punch、状态、时间范围、本人/管理范围、finding;3) 支持详情读取:状态、申请人/审批人脱敏摘要、字段摘要、动作历史、来源和 finding;4) 普通用户仅看本人作为申请人、参与人或动作处理人的记录;主管仅看直属下属申请和自己参与/操作过的记录,同部门非直属不可见;全量归档只允许 hr/admin/*;不得把 leave.view_all 或 attendance.view_all 单独解释为全量企微归档权限;5) callback-only、申请人未映射、参与人未映射或仅有外部 userid 的记录默认仅 hr/admin/* 可见;6) API 响应只返回脱敏外部键前缀和必要业务摘要;7) 单测必须证明查询路径不调用企微 access token、wecomApproval 写/读接口、补偿拉取或 callback crypto,也不读取 WECOM_AGENT_SECRET、WECOM_CALLBACK_TOKEN 或 WECOM_CALLBACK_ENCODING_AES_KEY。","受影响流程:OA 用户查看企微审批历史 -> 列表筛选 -> 查看详情 -> 对账 finding;验证步骤:cd server && node --check src/routes/wecomApprovalArchive.js;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;负例必须覆盖普通员工不可看他人记录、主管不能越过直属下属、同部门非直属不可见、finance/finance_mgr 仅有 attendance.view_all 或 leave.view_all 不得全量查看、详情 ID 猜测返回 403/404、scope=all 或 employeeId 过滤不能绕过权限、callback-only/未映射/仅外部 userid 只给 hr/admin/*、查询路径不读取企微 Secret 且不调用企微 API。","node|vitest","TODO","TODO","TODO","server/src/routes/wecomApprovalArchive.js|server/src/services/integrations/wecomApprovalArchive.js|server/tests/unit/routes/wecomApprovalArchive.test.js","[""WARCH2-0""]","回滚路径:移除新增路由注册和测试;不删除 WARCH1 已入库历史证据。不得新增 Prisma migration,除非实现方案另行批准。权限实现必须按 OA employee_id 关联授权,不得用外部 userid、脱敏前缀、display_summary、department_id、leave.view_all 或 attendance.view_all 作为普通用户/主管授权依据。"
"WARCH2-2","权限与脱敏门禁","固化 WARCH2 查询权限和隐私边界;完整外部键只留在 DB 内,默认 API、页面、日志和测试快照均不泄露。","1) 普通员工只能查看本人作为申请人、参与人或动作处理人的已归档历史;2) 审批人只能查看自己参与或操作过的已归档历史,不引入待办/可办理语义;3) 直属主管只能查看直属下属申请,不因 leave.view_all 或 attendance.view_all 获得全量;4) HR/管理员可查看请假/补卡归档范围;5) 原因摘要默认限权显示,列表不展示完整原因;6) API 白名单输出,不返回 normalized_value、value_preview、comment_summary、source_summary 原始对象、external_ref_summary、processing_error_message、error_message、完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、原始 payload、附件或评论。","受影响流程:历史查询 -> 权限过滤 -> 脱敏输出;验证步骤:cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;测试需 stringify 响应全文并断言不包含 normalized_value、value_preview、comment_summary、source_summary、external_ref_summary、processing_error_message、error_message、完整外部键、手机号、邮箱、token、Secret 或原始 payload;rg -n '完整 sp_no|完整 template_id|完整 userid|原始 payload|WARCH2' docs .agents/skills/hyb-oa-delivery/SKILL.md。","vitest|rg","TODO","TODO","TODO","server/tests/unit/routes/wecomApprovalArchive.test.js|docs/需求-统一审批中心规约.md|docs/管理员手册.md|.agents/skills/hyb-oa-delivery/SKILL.md","[""WARCH2-1""]","权限使用现有 authenticate / employee / permission 工具链;若权限模型缺口影响实现,先记录为 PARTIAL_QUERY_NEEDS_PERMISSION_DECISION,不扩大改造。本阶段暂不新增权限码,服务层明确等效语义:self/team/all,其中 all 仅 hr/admin/*;V1 不通用展示 normalized_value,即使 display_allowed=true 也只展示字段名、字段类型、敏感级别和服务端白名单摘要;后续扩展外出、加班、打卡或人事快照前再评估专用权限码。" "WARCH2-2","权限与脱敏门禁","固化 WARCH2 查询权限和隐私边界;完整外部键只留在 DB 内,默认 API、页面、日志和测试快照均不泄露。","1) 普通员工只能查看本人作为申请人、参与人或动作处理人的已归档历史;2) 审批人只能查看自己参与或操作过的已归档历史,不引入待办/可办理语义;3) 直属主管只能查看直属下属申请,不因 leave.view_all 或 attendance.view_all 获得全量;4) HR/管理员可查看请假/补卡归档范围;5) 原因摘要默认限权显示,列表不展示完整原因;6) API 白名单输出,不返回 normalized_value、value_preview、comment_summary、source_summary 原始对象、external_ref_summary、processing_error_message、error_message、完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、原始 payload、附件或评论。","受影响流程:历史查询 -> 权限过滤 -> 脱敏输出;验证步骤:cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;测试需 stringify 响应全文并断言不包含 normalized_value、value_preview、comment_summary、source_summary、external_ref_summary、processing_error_message、error_message、完整外部键、手机号、邮箱、token、Secret 或原始 payload;rg -n '完整 sp_no|完整 template_id|完整 userid|原始 payload|WARCH2' docs .agents/skills/hyb-oa-delivery/SKILL.md。","vitest|rg","TODO","TODO","TODO","server/tests/unit/routes/wecomApprovalArchive.test.js|docs/需求-统一审批中心规约.md|docs/管理员手册.md|.agents/skills/hyb-oa-delivery/SKILL.md","[""WARCH2-1""]","权限使用现有 authenticate / employee / permission 工具链;若权限模型缺口影响实现,先记录为 PARTIAL_QUERY_NEEDS_PERMISSION_DECISION,不扩大改造。本阶段暂不新增权限码,服务层明确等效语义:self/team/all,其中 all 仅 hr/admin/*;V1 不通用展示 normalized_value,即使 display_allowed=true 也只展示字段名、字段类型、敏感级别和服务端白名单摘要;后续扩展外出、加班、打卡或人事快照前再评估专用权限码。"
"WARCH2-3","前端最小历史查询页","新增或接入现有入口,提供请假/补卡企微审批历史最小查询体验;PC 管理视图和移动员工视图以可读、可筛选、可追溯为目标,不做完整镜像大屏。","1) PC 端可查看请假/补卡历史列表、状态、申请人、时间、来源、finding 提示和详情抽屉或详情区;2) 移动端员工可查看与本人相关的历史摘要和详情;3) 文案明确来源为企业微信主办、OA 自建留存;4) 同意单击风险以操作来源/审计提示体现;5) 页面无完整外部键、手机号、邮箱、原因全文默认泄露;6) 前端入口不得放在审批待办或待办动作语境,不展示审批按钮、pending 待办数或完整镜像暗示。","受影响流程:管理员/HR 查询历史 -> 员工移动端查自己的历史 -> 企微不可用时仍可查看 OA 已保存记录;验证步骤:cd client && npm run typecheck;cd client && npm run build;必要时补充 Playwright 或组件级人工步骤:登录管理员/员工 -> 打开历史页 -> 筛选请假/补卡 -> 查看详情;检查入口不在审批待办/移动审批语境,不显示审批按钮、pending 角标或可办理暗示。","npm|playwright|manual","TODO","TODO","TODO","client/src/api/wecomApprovalArchive.ts|client/src/pages/*Wecom*Archive*.tsx|client/src/pages/Mobile*Archive*.tsx|client/src/components/navigation/NavLinks.tsx|client/src/App.tsx","[""WARCH2-2""]","前端优先复用现有表格、移动卡片和状态 badge;不新建营销页,不做完整镜像仪表盘。入口建议使用备用模块或我的历史语境,固定文案:企业微信主办,OA 自建留存;仅已归档记录。不得放入 /workflow/tasks 审批待办上下文,不绑定移动底部审批 pending badge。回滚路径:移除新增页面/入口和 API 封装。" "WARCH2-3","前端最小历史查询页","新增或接入现有入口,提供请假/补卡企微审批历史最小查询体验;PC 管理视图和移动员工视图以可读、可筛选、可追溯为目标,不做完整镜像大屏。","1) PC 端可查看请假/补卡历史列表、状态、申请人、时间、来源、finding 提示和详情抽屉或详情区;2) 移动端员工可查看与本人相关的历史摘要和详情;3) 文案明确来源为企业微信主办、OA 自建留存;4) 同意单击风险以操作来源/审计提示体现;5) 页面无完整外部键、手机号、邮箱、原因全文默认泄露;6) 前端入口不得放在审批待办或待办动作语境,不展示审批按钮、pending 待办数或完整镜像暗示;7) 页面必须出现“企业微信主办,OA 自建留存”和“仅已归档记录”,并验证不处于 /workflow/tasks 审批待办语境。","受影响流程:管理员/HR 查询历史 -> 员工移动端查自己的历史 -> 企微不可用时仍可查看 OA 已保存记录;验证步骤:cd client && npm run typecheck;cd client && npm run build;必要时补充 Playwright 或组件级人工步骤:登录管理员/员工 -> 打开历史页 -> 筛选请假/补卡 -> 查看详情;检查入口不在审批待办/移动审批语境,不显示审批按钮、pending 角标或可办理暗示;检查页面包含“企业微信主办,OA 自建留存”和“仅已归档记录”,且 URL/导航不落入 /workflow/tasks 待办上下文。","npm|playwright|manual","TODO","TODO","TODO","client/src/api/wecomApprovalArchive.ts|client/src/pages/*Wecom*Archive*.tsx|client/src/pages/Mobile*Archive*.tsx|client/src/components/navigation/NavLinks.tsx|client/src/App.tsx","[""WARCH2-2""]","前端优先复用现有表格、移动卡片和状态 badge;不新建营销页,不做完整镜像仪表盘。入口建议使用备用模块或我的历史语境,固定文案:企业微信主办,OA 自建留存;仅已归档记录。不得放入 /workflow/tasks 审批待办上下文,不绑定移动底部审批 pending badge。回滚路径:移除新增页面/入口和 API 封装。"
"WARCH2-4","QA-only 离线与公网验证","补充 WARCH2 查询验收 runner 或复用 API smoke,证明不调用企微 API 时仍能通过正式 API/页面读取 WARCH1 已保存历史。","1) 本地可用测试数据或 mock 覆盖空态、2 条历史、finding 提示;2) 公网部署后 /ready 正常;3) 远端 API smoke 或 runner 在不调用企微 API 的情况下读取 OA DB 历史;4) 若远端无归档数据,记录 PARTIAL_ARCHIVE_NEEDS_DATA;5) public bundle scan 或 runtime smoke 通过。","受影响流程:部署 -> /ready -> OA DB 历史查询 -> 企微不可用兜底证明;验证步骤:SYNC_ENV=0 bash deploy/trialrun/deploy.sh;远端执行 npm run check:wecom-approval-archive -- --offline --format=json;如新增 API smoke,执行对应命令;复检 /ready 和 public bundle scan。","bash|node|ssh","TODO","TODO","TODO","server/src/scripts/check-wecom-approval-archive.js|scripts/qa/*|deploy/trialrun/deploy.sh","[""WARCH2-3""]","公网验证只读 OA DB,不写企微、不创建模板/审批单、不同步本地 env。" "WARCH2-4","QA-only 离线与公网验证","补充 WARCH2 查询验收 runner 或复用 API smoke,证明不调用企微 API 时仍能通过正式 API/页面读取 WARCH1 已保存历史。","1) 本地可用测试数据或 mock 覆盖空态、2 条历史、finding 提示;2) 公网部署后 /ready 正常;3) 远端 API smoke 或 runner 在不调用企微 API 的情况下读取 OA DB 历史;4) 若远端无归档数据,记录 PARTIAL_ARCHIVE_NEEDS_DATA;5) public bundle scan 或 runtime smoke 通过。","受影响流程:部署 -> /ready -> OA DB 历史查询 -> 企微不可用兜底证明;验证步骤:SYNC_ENV=0 bash deploy/trialrun/deploy.sh;远端执行 npm run check:wecom-approval-archive -- --offline --format=json;如新增 API smoke,执行对应命令;复检 /ready 和 public bundle scan。","bash|node|ssh","TODO","TODO","TODO","server/src/scripts/check-wecom-approval-archive.js|scripts/qa/*|deploy/trialrun/deploy.sh","[""WARCH2-3""]","公网验证只读 OA DB,不写企微、不创建模板/审批单、不同步本地 env。"
"WARCH2-5","事实源回写、门禁与提交","完成 WARCH2 实现后的文档回写、本地门禁、公网验证、Issue 状态回填和中文提交。","1) Issue 状态按实测结果回填;2) 路线图、API 能力目录、统一审批规约、企业微信基础设施规约、请假考勤规约、管理员手册、试运行报告、文档索引、事实源矩阵和 skill 同步 WARCH2 结果;3) 本地 server/client/docs/process gate 通过;4) 公网验证结果和报告路径写入事实源;5) 中文提交完成。","受影响流程:WARCH2 实现 -> 查询验收 -> 后续镜像准入;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --baseline --json;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;cd server && npm run prisma:validate;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;cd client && npm run typecheck;cd client && npm run build;node scripts/qa/audit-docs.mjs --check-registry;python3 /home/shunli/.codex/skills/.system/skill-creator/scripts/quick_validate.py .agents/skills/hyb-oa-delivery;git diff --check;bash scripts/check-minimal.sh。","python3|node|npm|vitest|bash|git","TODO","TODO","TODO","docs/企微优先开发路线图.md|docs/企微API能力目录.md|docs/需求-统一审批中心规约.md|docs/需求-企业微信基础设施规约.md|docs/需求-请假考勤修正规约.md|docs/管理员手册.md|docs/trialrun/人工试运行报告.md|docs/文档索引.md|docs/文档事实源状态矩阵.md|.agents/skills/hyb-oa-delivery/SKILL.md","[""WARCH2-4""]","提交信息建议:WARCH2 增加企微审批历史只读查询。WARCH2 完成后仍不直接放行完整镜像,下一步再决策外出/加班样例或镜像合同。" "WARCH2-5","事实源回写、门禁与提交","完成 WARCH2 实现后的文档回写、本地门禁、公网验证、Issue 状态回填和中文提交。","1) Issue 状态按实测结果回填;2) 路线图、API 能力目录、统一审批规约、企业微信基础设施规约、请假考勤规约、管理员手册、试运行报告、文档索引、事实源矩阵和 skill 同步 WARCH2 结果;3) 本地 server/client/docs/process gate 通过;4) 公网验证结果和报告路径写入事实源;5) 中文提交完成。","受影响流程:WARCH2 实现 -> 查询验收 -> 后续镜像准入;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --baseline --json;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;cd server && npm run prisma:validate;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;cd client && npm run typecheck;cd client && npm run build;node scripts/qa/audit-docs.mjs --check-registry;python3 /home/shunli/.codex/skills/.system/skill-creator/scripts/quick_validate.py .agents/skills/hyb-oa-delivery;git diff --check;bash scripts/check-minimal.sh。","python3|node|npm|vitest|bash|git","TODO","TODO","TODO","docs/企微优先开发路线图.md|docs/企微API能力目录.md|docs/需求-统一审批中心规约.md|docs/需求-企业微信基础设施规约.md|docs/需求-请假考勤修正规约.md|docs/管理员手册.md|docs/trialrun/人工试运行报告.md|docs/文档索引.md|docs/文档事实源状态矩阵.md|.agents/skills/hyb-oa-delivery/SKILL.md","[""WARCH2-4""]","提交信息建议:WARCH2 增加企微审批历史只读查询。WARCH2 完成后仍不直接放行完整镜像,下一步再决策外出/加班样例或镜像合同。"
1 ID Title Description Acceptance Test_Method Tools Dev_Status Review1_Status Regression_Status Files Dependencies Notes
2 WARCH2-0 只读查询合同与边界冻结 建立 WARCH2 企微审批历史只读查询 V1 合同;承接 WARCH1 已把请假/补卡历史写入 OA DB 并能离线读取,本阶段把 runner 级证明升级为正式 OA 可查能力。范围仅请假 + 补卡历史查询,不写企微、不创建模板、不提交审批、不开发外出/加班、不进入完整镜像、应急接管、恢复回写或 RuleOps。 1) 明确 WARCH2 是 WARCH1 后的正式查询切片;2) API 和页面均只读 OA DB,不调用企微 API;3) Secret 来源固定:WARCH2 查询自身不读取企微 Secret;若后续复用补偿读取,只能固定 WECOM_AGENT_SECRET,不尝试其他 Secret、无 fallback、不允许运行时猜 Secret;4) 不输出完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、表单原始 payload、附件或评论;5) 缺 OA 归档数据时输出空态或 PARTIAL_ARCHIVE_NEEDS_DATA,缺权限或外部配置时输出 NEEDS_CONFIG 或 SKIP/BLOCKED_BY_EXTERNAL_CONFIG,不伪造成镜像完成;6) 编码前给实现方案并获批。 受影响流程:企微主办请假/补卡 -> WARCH1 入库 -> OA 只读历史查询 -> 企微不可用时历史可查;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;人工批准实现方案后再编码。 python3|node|manual TODO TODO TODO issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv [] 本行仅合同,无 schema、无业务代码、无部署副作用。回滚/清理:删除本合同前不得启动实现;实现阶段需独立记录回滚路径。
3 WARCH2-1 后端只读查询 API 新增企微审批历史只读 API,优先复用 WARCH1 归档服务,从 OA DB 查询请假/补卡历史列表、详情、参与人、动作、字段摘要和对账 finding;不调用企微 API。 1) 新增路由默认挂在 /api/wecom/approval-archive 或同等内部路径;2) 支持列表筛选:类型 leave/missed_punch、状态、时间范围、本人/管理范围、finding;3) 支持详情读取:状态、申请人/审批人脱敏摘要、字段摘要、动作历史、来源和 finding;4) 普通用户仅看本人作为申请人、参与人或动作处理人的记录;主管仅看直属下属申请和自己参与/操作过的记录,同部门非直属不可见;全量归档只允许 hr/admin/*;不得把 leave.view_all 或 attendance.view_all 单独解释为全量企微归档权限;5) callback-only、申请人未映射、参与人未映射或仅有外部 userid 的记录默认仅 hr/admin/* 可见;6) API 响应只返回脱敏外部键前缀和必要业务摘要。 1) 新增路由默认挂在 /api/wecom/approval-archive 或同等内部路径;2) 支持列表筛选:类型 leave/missed_punch、状态、时间范围、本人/管理范围、finding;3) 支持详情读取:状态、申请人/审批人脱敏摘要、字段摘要、动作历史、来源和 finding;4) 普通用户仅看本人作为申请人、参与人或动作处理人的记录;主管仅看直属下属申请和自己参与/操作过的记录,同部门非直属不可见;全量归档只允许 hr/admin/*;不得把 leave.view_all 或 attendance.view_all 单独解释为全量企微归档权限;5) callback-only、申请人未映射、参与人未映射或仅有外部 userid 的记录默认仅 hr/admin/* 可见;6) API 响应只返回脱敏外部键前缀和必要业务摘要;7) 单测必须证明查询路径不调用企微 access token、wecomApproval 写/读接口、补偿拉取或 callback crypto,也不读取 WECOM_AGENT_SECRET、WECOM_CALLBACK_TOKEN 或 WECOM_CALLBACK_ENCODING_AES_KEY。 受影响流程:OA 用户查看企微审批历史 -> 列表筛选 -> 查看详情 -> 对账 finding;验证步骤:cd server && node --check src/routes/wecomApprovalArchive.js;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;负例必须覆盖普通员工不可看他人记录、主管不能越过直属下属、同部门非直属不可见、finance/finance_mgr 仅有 attendance.view_all 或 leave.view_all 不得全量查看、详情 ID 猜测返回 403/404、scope=all 或 employeeId 过滤不能绕过权限、callback-only/未映射/仅外部 userid 只给 hr/admin/*。 受影响流程:OA 用户查看企微审批历史 -> 列表筛选 -> 查看详情 -> 对账 finding;验证步骤:cd server && node --check src/routes/wecomApprovalArchive.js;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;负例必须覆盖普通员工不可看他人记录、主管不能越过直属下属、同部门非直属不可见、finance/finance_mgr 仅有 attendance.view_all 或 leave.view_all 不得全量查看、详情 ID 猜测返回 403/404、scope=all 或 employeeId 过滤不能绕过权限、callback-only/未映射/仅外部 userid 只给 hr/admin/*、查询路径不读取企微 Secret 且不调用企微 API。 node|vitest TODO TODO TODO server/src/routes/wecomApprovalArchive.js|server/src/services/integrations/wecomApprovalArchive.js|server/tests/unit/routes/wecomApprovalArchive.test.js ["WARCH2-0"] 回滚路径:移除新增路由注册和测试;不删除 WARCH1 已入库历史证据。不得新增 Prisma migration,除非实现方案另行批准。权限实现必须按 OA employee_id 关联授权,不得用外部 userid、脱敏前缀、display_summary、department_id、leave.view_all 或 attendance.view_all 作为普通用户/主管授权依据。
4 WARCH2-2 权限与脱敏门禁 固化 WARCH2 查询权限和隐私边界;完整外部键只留在 DB 内,默认 API、页面、日志和测试快照均不泄露。 1) 普通员工只能查看本人作为申请人、参与人或动作处理人的已归档历史;2) 审批人只能查看自己参与或操作过的已归档历史,不引入待办/可办理语义;3) 直属主管只能查看直属下属申请,不因 leave.view_all 或 attendance.view_all 获得全量;4) HR/管理员可查看请假/补卡归档范围;5) 原因摘要默认限权显示,列表不展示完整原因;6) API 白名单输出,不返回 normalized_value、value_preview、comment_summary、source_summary 原始对象、external_ref_summary、processing_error_message、error_message、完整 sp_no、template_id、userid、手机号、邮箱、token、Secret、EncodingAESKey、原始 XML、密文、原始 payload、附件或评论。 受影响流程:历史查询 -> 权限过滤 -> 脱敏输出;验证步骤:cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;测试需 stringify 响应全文并断言不包含 normalized_value、value_preview、comment_summary、source_summary、external_ref_summary、processing_error_message、error_message、完整外部键、手机号、邮箱、token、Secret 或原始 payload;rg -n '完整 sp_no|完整 template_id|完整 userid|原始 payload|WARCH2' docs .agents/skills/hyb-oa-delivery/SKILL.md。 vitest|rg TODO TODO TODO server/tests/unit/routes/wecomApprovalArchive.test.js|docs/需求-统一审批中心规约.md|docs/管理员手册.md|.agents/skills/hyb-oa-delivery/SKILL.md ["WARCH2-1"] 权限使用现有 authenticate / employee / permission 工具链;若权限模型缺口影响实现,先记录为 PARTIAL_QUERY_NEEDS_PERMISSION_DECISION,不扩大改造。本阶段暂不新增权限码,服务层明确等效语义:self/team/all,其中 all 仅 hr/admin/*;V1 不通用展示 normalized_value,即使 display_allowed=true 也只展示字段名、字段类型、敏感级别和服务端白名单摘要;后续扩展外出、加班、打卡或人事快照前再评估专用权限码。
5 WARCH2-3 前端最小历史查询页 新增或接入现有入口,提供请假/补卡企微审批历史最小查询体验;PC 管理视图和移动员工视图以可读、可筛选、可追溯为目标,不做完整镜像大屏。 1) PC 端可查看请假/补卡历史列表、状态、申请人、时间、来源、finding 提示和详情抽屉或详情区;2) 移动端员工可查看与本人相关的历史摘要和详情;3) 文案明确来源为企业微信主办、OA 自建留存;4) 同意单击风险以操作来源/审计提示体现;5) 页面无完整外部键、手机号、邮箱、原因全文默认泄露;6) 前端入口不得放在审批待办或待办动作语境,不展示审批按钮、pending 待办数或完整镜像暗示。 1) PC 端可查看请假/补卡历史列表、状态、申请人、时间、来源、finding 提示和详情抽屉或详情区;2) 移动端员工可查看与本人相关的历史摘要和详情;3) 文案明确来源为企业微信主办、OA 自建留存;4) 同意单击风险以操作来源/审计提示体现;5) 页面无完整外部键、手机号、邮箱、原因全文默认泄露;6) 前端入口不得放在审批待办或待办动作语境,不展示审批按钮、pending 待办数或完整镜像暗示;7) 页面必须出现“企业微信主办,OA 自建留存”和“仅已归档记录”,并验证不处于 /workflow/tasks 审批待办语境。 受影响流程:管理员/HR 查询历史 -> 员工移动端查自己的历史 -> 企微不可用时仍可查看 OA 已保存记录;验证步骤:cd client && npm run typecheck;cd client && npm run build;必要时补充 Playwright 或组件级人工步骤:登录管理员/员工 -> 打开历史页 -> 筛选请假/补卡 -> 查看详情;检查入口不在审批待办/移动审批语境,不显示审批按钮、pending 角标或可办理暗示。 受影响流程:管理员/HR 查询历史 -> 员工移动端查自己的历史 -> 企微不可用时仍可查看 OA 已保存记录;验证步骤:cd client && npm run typecheck;cd client && npm run build;必要时补充 Playwright 或组件级人工步骤:登录管理员/员工 -> 打开历史页 -> 筛选请假/补卡 -> 查看详情;检查入口不在审批待办/移动审批语境,不显示审批按钮、pending 角标或可办理暗示;检查页面包含“企业微信主办,OA 自建留存”和“仅已归档记录”,且 URL/导航不落入 /workflow/tasks 待办上下文。 npm|playwright|manual TODO TODO TODO client/src/api/wecomApprovalArchive.ts|client/src/pages/*Wecom*Archive*.tsx|client/src/pages/Mobile*Archive*.tsx|client/src/components/navigation/NavLinks.tsx|client/src/App.tsx ["WARCH2-2"] 前端优先复用现有表格、移动卡片和状态 badge;不新建营销页,不做完整镜像仪表盘。入口建议使用备用模块或我的历史语境,固定文案:企业微信主办,OA 自建留存;仅已归档记录。不得放入 /workflow/tasks 审批待办上下文,不绑定移动底部审批 pending badge。回滚路径:移除新增页面/入口和 API 封装。
6 WARCH2-4 QA-only 离线与公网验证 补充 WARCH2 查询验收 runner 或复用 API smoke,证明不调用企微 API 时仍能通过正式 API/页面读取 WARCH1 已保存历史。 1) 本地可用测试数据或 mock 覆盖空态、2 条历史、finding 提示;2) 公网部署后 /ready 正常;3) 远端 API smoke 或 runner 在不调用企微 API 的情况下读取 OA DB 历史;4) 若远端无归档数据,记录 PARTIAL_ARCHIVE_NEEDS_DATA;5) public bundle scan 或 runtime smoke 通过。 受影响流程:部署 -> /ready -> OA DB 历史查询 -> 企微不可用兜底证明;验证步骤:SYNC_ENV=0 bash deploy/trialrun/deploy.sh;远端执行 npm run check:wecom-approval-archive -- --offline --format=json;如新增 API smoke,执行对应命令;复检 /ready 和 public bundle scan。 bash|node|ssh TODO TODO TODO server/src/scripts/check-wecom-approval-archive.js|scripts/qa/*|deploy/trialrun/deploy.sh ["WARCH2-3"] 公网验证只读 OA DB,不写企微、不创建模板/审批单、不同步本地 env。
7 WARCH2-5 事实源回写、门禁与提交 完成 WARCH2 实现后的文档回写、本地门禁、公网验证、Issue 状态回填和中文提交。 1) Issue 状态按实测结果回填;2) 路线图、API 能力目录、统一审批规约、企业微信基础设施规约、请假考勤规约、管理员手册、试运行报告、文档索引、事实源矩阵和 skill 同步 WARCH2 结果;3) 本地 server/client/docs/process gate 通过;4) 公网验证结果和报告路径写入事实源;5) 中文提交完成。 受影响流程:WARCH2 实现 -> 查询验收 -> 后续镜像准入;验证步骤:python3 /home/shunli/.codex/skills/plan/scripts/validate_issues_csv.py issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv;node scripts/qa/check-process-contract.mjs --baseline --json;node scripts/qa/check-process-contract.mjs --issue issues/2026-05-20_00-26-04-wecom-approval-archive-query-v1.csv --profile wecom --json;cd server && npm run prisma:validate;cd server && npx vitest run tests/unit/routes/wecomApprovalArchive.test.js tests/unit/services/wecomApprovalArchive.test.js --reporter=verbose;cd client && npm run typecheck;cd client && npm run build;node scripts/qa/audit-docs.mjs --check-registry;python3 /home/shunli/.codex/skills/.system/skill-creator/scripts/quick_validate.py .agents/skills/hyb-oa-delivery;git diff --check;bash scripts/check-minimal.sh。 python3|node|npm|vitest|bash|git TODO TODO TODO docs/企微优先开发路线图.md|docs/企微API能力目录.md|docs/需求-统一审批中心规约.md|docs/需求-企业微信基础设施规约.md|docs/需求-请假考勤修正规约.md|docs/管理员手册.md|docs/trialrun/人工试运行报告.md|docs/文档索引.md|docs/文档事实源状态矩阵.md|.agents/skills/hyb-oa-delivery/SKILL.md ["WARCH2-4"] 提交信息建议:WARCH2 增加企微审批历史只读查询。WARCH2 完成后仍不直接放行完整镜像,下一步再决策外出/加班样例或镜像合同。