SW-02 spec_sha 分域哈希:spec 小编订不再使全量内容缓存失效 - #9
Conversation
- provenance.spec_domain_fingerprints:按 spec 顶层子域取 sha256[:12] - PassContext.spec_shas 新字段(默认空 = 旧语义回退),cache_versions 的 spec_sha 缩域为 ir+passes(CACHE_SPEC_DOMAINS);checks 由既有 ruleset_ver 单独覆盖,rubrics/feedback/rules 等不进缓存键 - runs 表 provenance 仍是全量 spec_sha,不弱化 - 接线:cli._make_ctx + eval/l1.py 两处编译入口 - 测试:tests/test_spec_domains.py(4 例,先红后绿)
There was a problem hiding this comment.
🟡 Changes recommended
Address the missing rules cache dependency for p5_dialogue and safely fall back when required spec domains are incomplete.
Once you've addressed the issues Copilot identified, you can request another Copilot review.
Pull request overview
This PR adds domain-scoped spec fingerprints to reduce unrelated cache invalidation while preserving full provenance hashes.
Changes:
- Adds per-domain SHA-256 fingerprints.
- Uses
irandpassesdomains for cache keys. - Wires fingerprints into CLI and evaluation paths with tests.
File summaries
| File | Summary |
|---|---|
tests/test_spec_domains.py |
Tests domain hashing and cache behavior. |
src/nsc/runtime/provenance.py |
Implements per-domain fingerprints. |
src/nsc/passes/__init__.py |
Adds scoped cache-key support. |
src/nsc/eval/l1.py |
Wires fingerprints into evaluation contexts. |
src/nsc/cli.py |
Wires fingerprints into CLI contexts. |
Review details
Suppressed comments (1)
src/nsc/cli.py:37
- SW-02 的接线仍漏掉了
scripts/stress_generalize.py::_ctx_for:它也创建PassContext并运行带@cached_pass的完整 pipeline,但没有传spec_shas,所以压测入口仍会因 rubrics/feedback/rules 等无关 spec 编辑而回退到全量缓存失效。请将该编译入口纳入同样的分域接线,或明确把它排除在本 PR 的缓存语义之外。
spec_shas=spec_domain_fingerprints(), # SW-02:缓存键分域;provenance 仍全量
- Files reviewed: 5/5 changed files
- Comments generated: 2
- Review effort level: Lite
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
| #: 进缓存键的 spec 域(SW-02):只含影响生成结构的域;checks 由 ruleset_ver 覆盖。 | ||
| CACHE_SPEC_DOMAINS = ("ir", "passes") |
There was a problem hiding this comment.
已修正(fae8bae):采纳"按 pass 声明域"方案——新增 PASS_EXTRA_SPEC_DOMAINS = {"p5_dialogue": ("rules",)},scoped_spec_sha(pass_name) 取基础域 ∪ 该 pass 的额外域。现在 spec/rules/L3_canonical 的编辑会使 p5 缓存失效、不牵连 p3 等不读该域的 pass。回归测试 test_rules_domain_only_invalidates_p5(规则编辑 → p5 键变、p3 键不变)。关于建议中的 p5 cache miss 回归测试:键级断言(cache_versions 的 spec_sha 组成变化)与 cache miss 是同义变形(cached_pass 用 cache_versions 组键),已由 test_cache.py 的失效语义测试 + 本测试共同覆盖。
| if not self.spec_shas: | ||
| return self.spec_sha | ||
| return "|".join(f"{d}:{self.spec_shas.get(d, '')}" for d in CACHE_SPEC_DOMAINS) |
There was a problem hiding this comment.
已修正(fae8bae):scoped_spec_sha 在任一必需域(含该 pass 的额外域)缺失时回退全量 spec_sha——宁可多失效、不可少失效。回归测试 test_partial_domain_map_falls_back_to_full_sha(只给 {ir: ...} 时 p3/p5 都用 full123)。
Copilot review(PR #9): - p5 self-check 经 revision_brief 读 spec/rules/L3_canonical(VOICE RULES), ruleset_ver 只覆盖 spec/checks → 规则编辑后 p5 命中旧缓存。新增 PASS_EXTRA_SPEC_DOMAINS = {p5_dialogue: (rules,)},scoped_spec_sha 按 pass 取并集(review 建议的按 pass 声明域) - spec_shas 缺任一必需域时回退全量 spec_sha,不再拼 'ir:|passes:' 式弱化失效条件的键 - 回归:test_rules_domain_only_invalidates_p5 / test_partial_domain_map_falls_back_to_full_sha
这个 PR 改的是哪一层?(必选其一)
spec/profiles/brands/cases/export/)→ 必须打标签asset-change并附 ADRsrc/tests/)→ 无需 ADR(未改 spec/ 内容,只加了指纹计算函数)工单
Closes # · 工单号:SW-02(上游依赖卡,Lab 仓 docs/WORK_ORDERS.md §上游依赖卡)
问题
_make_ctx/eval/l1.py此前把 全量 spec 指纹(spec//*.py + *.yaml 联合 sha256)放进每个 pass 的缓存键:任何一处 spec 小编订(如改一条 rubric、一个 budget)都会使全量**内容缓存失效,重跑整季 LLM 编译。改动
provenance.spec_domain_fingerprints():按 spec 顶层子域(checks/ir/passes/rubrics/feedback/rules/brand/root)分别取 sha256[:12]PassContext.spec_shas新字段(默认空 dict = 旧语义原样回退,既有调用方/测试不受影响);cache_versions()的 spec_sha 改用scoped_spec_sha():只含 ir + passes(CACHE_SPEC_DOMAINS,影响生成结构的域)ruleset_ver使缓存失效;rubrics/feedback/rules 等与生成无关的域不再牵连cli._make_ctx、eval/l1.py两处编译入口验收命令(贴出你本地跑通的输出)
注:唯一失败
test_db_export_fresh源于本机工作树一份未提交的 cases/cases.db 改动(禁止提交的运行现场);origin/main 干净 worktree 上该测试通过,本 PR 未触碰该文件。检查表
ImportError: cannot import name 'spec_domain_fingerprints')prompts/影响生成结果吗?