- README.md is now the product/repo front door (architecture, repo map, local dev, test tiers, delivery flow, doc map). Engine positioning, VedAstro/Codex setup and the oracle/benchmark command reference move verbatim to docs/engine/README.md, docs/engine/vedastro-gateway.md and docs/benchmark/README.md. Capability badges realigned with the registry (91/78/8/0); tests/test_readme_badges.py was red on staging. - AGENTS.md: Part A (environment truth, delivery, worktrees, record placement, bug workflow, growth freeze, frontend red lines, privacy, pre-work check, test tiers) and Part B (reading-rigor constraints). GitHub issue-tracker/triage boilerplate removed: GitHub is a read-only mirror. All strings locked by tests/ are preserved. - CLAUDE.md added: roles, three working modes, task-brief sections, acceptance criteria, session discipline; imports AGENTS.md. - 50 tracked TASK-*/PROGRESS-* files and 3 never-committed briefs move to docs/tasks/ with an index; REPO_LAYOUT.md merged into README. Docs-only change (no gated path touched). Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_0193vBv6w5MV2cifdTUu9H5P
13 KiB
任务书 · 个人报告全主题 blocked 修复(2026-09-02)
基线:origin/staging @ 24a1cf37。
事故实证
2026-09-02 15:45 staging 真实生成的 personal_full 报告(请求主题 career/marriage/timing/wealth)四个主题全部 blocked,摘要退化为"报告主题尚未生成"。blocked 理由:
- career:缺少最低证据组 AmK、Transit
- marriage:缺少最低证据组 DK
- timing:缺少最低证据组 Transit
- wealth:缺少结构化分盘 D2、D11
已在本地用 origin/staging @ 24a1cf37 的前端提取层 + 同版本 Python 引擎(scripts/jyotish_api_server.py,虚构 smoke 出生数据,按 worker 的方式每主题一次 /api/consultation_workflow)完整复现:blocked 主题与理由逐字一致。这是确定性缺陷,不是线上环境问题。
根因(已逐项定位,不需要重新猜)
根因 1(wealth):分盘值形状不匹配,所有分盘图提取失败。
引擎 chart.modules.varga_full 的值形状是:
{ "ascendant": { "sign": "Gemini", "sign_index": 2, "degree": 21.027 },
"planets": { "Sun": { "sign": "Libra", "sign_index": 6, "degree": 15.23, "house": 5 }, ... },
"house_chart": [["Ketu"], [], ...], "division": ..., "name": ..., "meaning": ... }
而 frontend/src/lib/personal-report-generation.ts 的 deriveVargaHousesFromEngine(约 :336)读的是大写 Ascendant + sign_idx + 顶层行星键 → 每张分盘都返回 null → bundle charts 只剩 D1。昨日 45f190a1 修了键名别名(D2_Hora→D2)并新增"claim card 主题缺结构化分盘图则降 blocked"的兜底(demoteThemesMissingRequiredCharts),但没修值形状——于是 wealth 从"write 后文档校验失败"变成"bundle 层 blocked"。643f6f7a 的 fixture 是按旧形状手造的,所以测试全绿、线上照挂。(2026-08-30 观察到的 final_parse_rejected 大概率同源。)
根因 2(timing、career 之一半):Transit 回执从不生成。
引擎响应 chart.modules.transits 存在且 status: "executed"(含 sade_sati、triggers、search_period、boundary),但 consumer_context.available_layers 与 machine packet sections 里都没有 transit 名目,前端提取层从不为它 upsert 执行回执 → 要求 Transit 的 timing/career 自这套 claim gate 上线起从未通过。存量问题。
根因 3(career:AmK、marriage:DK):consultation 响应没有 Chara Karaka 数据。
整个响应中无 Amatyakaraka/Darakaraka 数值层:chart.modules.jaimini 只有 arudha_padas;guided topics 里 DK 的值是空占位符 - H-。引擎的 full-reading 路径有现成 karaka 计算(scripts/jaimini.py),但 scripts/jyotish_api_server.py 的 _attach_local_consultation_layers 没有把这层挂进 consultation 响应。前端修不了,必须引擎响应新增字段。
决策记录
产品负责人 2026-09-02 确认修复方向并授权:
- (a) 引擎侧允许在 consultation 响应中新增 Chara Karaka 字段(这是
TASK-report-skill-parity-20260901.md任务 0 预留的"响应新增字段"止损分支,正式启用)。仍然只许新增、不许改动既有字段的键名、形状或语义。 - (b)
643f6f7a/ 既有测试中按旧分盘形状手造的 fixture 与断言,属于"锁住本轮要修的缺陷本身",允许按红线 9 的程序修改(注明原值与原因)。 - (c) 主题最低证据组(
report-theme-evidence-plan.ts)不在授权范围内:不得为了让主题通过而删除或放宽 AmK/DK/Transit/D2/D11 要求。修法只能是把证据真实供给上。
硬红线
- 最低证据组一条不得放宽(见决策记录 c)。
demoteThemesMissingRequiredCharts兜底保留,不得删除——修好值形状后它自然不触发。 - 引擎改动只许响应新增字段:不改既有字段、不改排盘算法、不改 full-reading 路径;新增层必须复用
scripts/jaimini.py既有实现,不得重写 karaka 算法。 - fixture 必须来自真实引擎响应(golden),不得再手造形状。任务 0 是门控:先落 golden fixture 与形状契约测试,任务 1–3 的实现测试必须建立在它之上。
- 上一轮任务书(
TASK-report-skill-parity-20260901.md)的红线继续有效:输入隔离不放松、writer 输出 schema 只可收紧、assertionLevel推导与 consensus ≥2 verified 防升级校验一字不改、本轮不改数据库结构、章节串行、telemetry 只记指标名与数值。 - 隐私红线:fixture 与测试只用虚构 smoke 出生数据;golden fixture 入库前确认不含任何真实用户资料。
- 推 staging 前
./node_modules/.bin/tsc --noEmit必须通过(不要用npx tsc,会装到空包tsc@2.0.4)。不得改.gitea/workflows/**,不得自行提升 main。 - Python 侧改动必须带单元测试(
.venv+ unittest/pytest,按仓内既有测试形式),并真实跑过。
让步顺序:数据不损坏 > 证据纪律不回退 > 功能与测试不回归 > 可验证的修复 > 成本 > 代码整洁。
开工前置
git fetch origin --prune
git worktree add -b codex/report-blocked-repairs-20260902 \
../.worktrees/report-blocked-repairs-20260902 origin/staging
读 pre_work_error_ledger.md,跑 scripts/pre_work_check.py,读 frontend/AGENTS.md,在 docs/BUG_HISTORY.md 检索(BUG-486 及相邻条目与本轮直接相关)。
先读这几处再动手:
frontend/src/lib/personal-report-generation.ts——deriveVargaHousesFromEngine(:336 附近)、readAllVargaCharts/readVargaHouses(VARGA_KEY_ALIASES已存在)、demoteThemesMissingRequiredCharts、receipt upsert 逻辑frontend/src/lib/report-theme-evidence-plan.ts—— 各主题requiredTechniqueGroups(只读,不改)scripts/jyotish_api_server.py——_attach_local_consultation_layers、execute_consultation_workflowscripts/jaimini.py—— 既有 Chara Karaka 实现git show 45f190a1与git show 643f6f7a—— 昨日两次治标修复的全部内容
复现方法(验收也用它)
起本地引擎:.venv/bin/python scripts/jyotish_api_server.py --port 5200。用虚构出生数据(如 1993-06-15 10:30,lat 36.42 / lon 114.21 / tz 8)按 worker 的调用方式(entryMode: "direct_chart",question 请为个人报告计算 <theme> 主题证据)对 career/marriage/timing/wealth 各调一次 runConsultationWorkflow,把 4 个响应喂给 buildReportEvidenceBundleV2,检查 claimCards / blockedSections / executionLedger / charts。修复前的预期输出(用于确认复现成功):claimCards 为空、四主题全在 blockedSections、charts 只有 D1。
任务 0(P0,门控)· Golden fixture 与形状契约
做法
- 用上述复现方法捕获 4 个主题的真实响应,裁剪成 fixture(保留
chart.modules.varga_full(至少 D2/D9/D10/D11/D24 各一张完整值)、modules.transits、modules.jaimini、consumer_context、machine packet sections;删除与提取无关的大块字段以控制体积),入库为测试资产。 - 新增形状契约测试:断言 varga_full 值的真实形状(小写
ascendant、sign_index、planets字典、house_chart),并断言modules.transits.status字段存在。这个测试在修复前就应该通过(它锁的是引擎真实形状,不是前端行为)。 - 将
643f6f7a手造的旧形状 fixture 替换为 golden 派生数据;按红线 9 在改动处注明原值与原因。
验收
- 形状契约测试直接对 golden fixture 通过;PROGRESS 记录 fixture 的捕获命令与裁剪规则。
任务 1(P0)· 修分盘值形状,复活结构化分盘图
做法
deriveVargaHousesFromEngine 兼容真实形状,规则:
- 上升:
varga.ascendant ?? varga.Ascendant;星座索引sign_index ?? sign_idx ?? signIndex(sign);度数degree ?? degree_in_sign。 - 行星:优先读
varga.planets字典(每行星有sign_index与house,宫位可直接用house,无house时按整星座宫从上升推导);planets不存在时退回旧的顶层行星键路径(保持对旧形状的兼容,两种形状都要有测试)。 - 不吸收
house_chart以外来源不明的字段;未知键一律不复制。
验收
- 单元测试双形状覆盖(golden 新形状 + 既有旧形状)。
- 复现管线跑通后:
charts至少含 D1/D2/D9/D10/D11/D24;wealth 出 claim card,demoteThemesMissingRequiredCharts不触发;D2/D11 回执 executed。 - education / migration_home 等依赖分盘的主题在补充复现(9 主题全请求)中同样解锁,PROGRESS 记录逐主题结果。
任务 2(P0)· Transit 执行回执
做法
提取层读 chart.modules.transits:status === "executed" 时 upsert Transit 回执(status: "partial"、executed: true,与 ashtakavarga/dasha_sub_periods 的既有读取方式同风格);status 缺失或非 executed 时不产回执(fail closed,不得默认 executed)。
验收
- 单元测试:executed / 缺失 / 其他 status 三种输入。
- 复现管线:timing 出 claim card;career 的 blocked 理由只剩 AmK(在任务 3 完成前)。
任务 3(P0)· 引擎挂 Chara Karaka + 前端 AmK/DK 回执
做法
- 引擎:
_attach_local_consultation_layers调用scripts/jaimini.py既有实现,把 Chara Karaka 挂到chart.modules.jaimini.chara_karakas(结构建议:{ "AmK": { "planet": ..., ... }, "DK": { ... }, ... },具体键名以 jaimini.py 现有输出为准,新增字段不改既有arudha_padas)。带 Python 单元测试。 - 前端:从
modules.jaimini.chara_karakas中 AmK/DK 的存在性 upsertAmK/DK回执(partial+executed: true);数据缺失时不产回执。 - golden fixture 用引擎修复后的响应重新捕获(或叠加一份含 karakas 的 golden),形状契约测试同步覆盖新层。
验收
- Python 测试:consultation 响应含
chara_karakas且 AmK/DK 数据来自 jaimini.py 现有输出。 - 复现管线:career/marriage/timing/wealth 四主题全部出 claim card,blockedSections 为空;
executionLedger中 AmK/DK/Transit/D2/D11 均 executed。
止损
- 若
jaimini.py现有实现无法在 consultation 输入上直接复用(缺参数、口径冲突),停下写BLOCKED.md,不得重写算法、不得放宽最低证据组来绕过。
任务 4(P1)· 端到端与既有欠账
- 全套质量门:frontend
tsc --noEmit/eslint(0 error)/tsx --test(失败清单与基线逐条比对)/next build;Python 相关测试真实跑过。 - 部署后(委托方核对 health gitCommit)真实生成一份 personal_full 报告,验收:四主题有正文、不再全 blocked;顺带补上一轮欠的交付物——真实 writer 输出回溯抽查(≥3 处)与每章实测
inputTokens/墙钟对照(对照基线与 2 倍线裁决记录见PROGRESS-report-skill-parity-20260901.md与BLOCKED.md对应条目)。
不在本轮范围
- 主题最低证据组的增删改(决策记录 c)。
- 引擎排盘算法、full-reading 路径、varga_full 既有形状的任何改动。
- 知识包内容、writer prompt、成本优化(沿用已裁决结论)。
- 章节并发、模型更换、计费、数据库结构。
收尾
- PROGRESS 文件名写
PROGRESS-report-blocked-repairs-20260902.md。 docs/BUG_HISTORY.md新增条目(编号先对远端确认;根因 1 与 BUG-486 关联,注明 45f190a1/643f6f7a 是治标、本轮治本)。- 建议两次推送:任务 0+1+2(纯前端)一次;任务 3(引擎+前端)一次。staging push 触发全量构建+部署,全链路约 20 分钟,推送后核对
https://staging.jyotisha.chat/api/health的.deployment.gitCommit。 - 不自行提升 main。
交付物清单
- Golden fixture(真实响应派生)+ 形状契约测试;643f6f7a 旧 fixture 的替换说明
deriveVargaHousesFromEngine双形状兼容 + 测试;复现管线中 charts/D2/D11 复活证据- Transit 回执提取 + 三态测试
- 引擎
chara_karakas新增层 + Python 测试;前端 AmK/DK 回执 + 测试 - 复现管线修复前后对照:blockedSections 从 4 → 0,claimCards 从 0 → 4(9 主题全请求的逐主题表)
- 部署后真实报告验收 + 上一轮欠账(writer 输出回溯抽查、实测 tokens/墙钟对照)
docs/BUG_HISTORY.md条目、BLOCKED.md(任何触发止损的项)、PROGRESS-report-blocked-repairs-20260902.md- 全套质量门实际输出(frontend 四件 + Python 测试)