fix(varga): port the five sarpa ranges and the 22nd drekkana house (BUG-1494, BUG-1495, issue #159)
Upstream 50847e57, ported semantically: - Sarpa Drekkana now accepts the five classical ranges (Cancer 2/3, Scorpio 1/2, Pisces 3) and partitions on the raw longitude instead of the rounded display degrees. - The 22nd Drekkana is the eighth house of D3 (+7), not +21 zodiacal ten-degree divisions. scripts/varga.py is part of the extended frozen identity, so the sealed holdout and the reported-offset sweep were re-frozen under ERR-110: 20/20 sealed trials and 900/900 sweep trials match the sync8 records on every compared field, and the metrics, summary and widening geometry are unchanged. Tests: the upstream varga/ sarpa files are added under tests/test_upstream_sync9b_*.py; the stale +21 assertion and the sarpa definition string are updated with the original/new/reason columns in PROGRESS. Co-Authored-By: Grok (agent loop)
This commit is contained in:
co-authored by
Grok (agent loop)
parent
2243220841
commit
5c5f333d4d
@@ -1,5 +1,12 @@
|
||||
# 印度占星 Skill 更新日志
|
||||
|
||||
## 2026-10-28 — 两处分盘敏感点按来源修正
|
||||
|
||||
- Sarpa Drekkana 从三段补成书上的五段:巨蟹第 3 段、天蝎第 2 段以前漏掉,现在会标出来;正好落在 10 度边界上的盘不再划到上一段。
|
||||
- 第 22 号 Drekkana 改为 D3 的第 8 宫(以前多移了 14 个星座)。这个点目前还没接进完整解读的敏感点表,所以报告上看不到差别。
|
||||
- 生时校正 20 条密封案例与 900 个报时窗口,名次与分钟误差与上一份回放逐条相同。
|
||||
- Skill 版本不变(BUG-1494、BUG-1495,issue #159)。
|
||||
|
||||
## 2026-10-28 — 两人同时做校正或生成报告时不再互相拖慢
|
||||
|
||||
- 排盘服务把最重的三类计算(生时校正打分、24 小时分块扫描、长报告参考)放到两个独立的工作进程里。两个人同时算时,各自的等待时间和一个人单独算差不多(以前接近翻倍)。结果不变。
|
||||
|
||||
@@ -20416,3 +20416,34 @@
|
||||
- 关联:ERR-111(特征指纹随哈希种子变)、BUG-1482(#132 让模块能按名字被子进程找到)。
|
||||
- 复发自:无
|
||||
- 修复版本:分支 `codex/heavy-compute-processes-20261028`。
|
||||
|
||||
|
||||
## BUG-1494 | Sarpa Drekkana 少两段,边界还按四舍五入后的度数判段
|
||||
|
||||
- 状态:resolved(代码 + 回归测试;待部署)
|
||||
- 首次发现 / 最近更新:2026-10-28 / 2026-10-28(issue #159,上游 `50847e57`)
|
||||
- 影响面:完整解读里的 Sarpa Drekkana 标记。`scripts/varga.py`。
|
||||
- 现象:只认 Cancer-2、Scorpio-1、Pisces-3 三段。Raman《Hindu Predictive Astrology》Drekkana 章是五段,Cancer-3 与 Scorpio-2 漏掉。判段还先把星座内度数四舍五入到 4 位再整除,边界附近会划到上一段。
|
||||
- 触发条件:行星或上升落在被漏掉的两段,或经度正好在 10 度边界附近(如 100.0、220.0、360.0)。
|
||||
- 根因:`SARPA_DREKKANA_SIGNS` 一个星座只记一个段号;`int(round(deg,4)/10)+1` 让 99.99999 与 100.0 之类的边界口径不稳。
|
||||
- 修复:每星座改成段号元组(Cancer 2/3、Scorpio 1/2、Pisces 3),用原始经度 `int((lon % 30) / 10) + 1` 判段,`definition` 改成五段文字。生时校正不读这两个函数。
|
||||
- 验证:`tests/test_upstream_sync9b_sarpa_precision.py`(6 条边界参数化)、`tests/test_upstream_sync9b_varga_bphs.py`(36 段全枚举与五段区间断言)、`tests/test_varga_bphs.py` 通过。密封校正 20 条与报时窗口 900 条与上一份记录逐条相同。
|
||||
- 防复发:36 段全枚举 + 区间边界测试;判段只用原始经度,不再用显示用的四舍五入度数。
|
||||
- 关联:BUG-1495。
|
||||
- 复发自:无。
|
||||
- 修复版本:分支 `codex/upstream-sync9b-20261028`。
|
||||
|
||||
## BUG-1495 | 第 22 号 Drekkana 按 21 个十度分段取,多移了 14 个星座
|
||||
|
||||
- 状态:resolved(代码 + 回归测试;待部署)
|
||||
- 首次发现 / 最近更新:2026-10-28 / 2026-10-28(issue #159,上游 `50847e57`)
|
||||
- 影响面:`scripts/varga.py::calc_22nd_drekkana`。全仓只有单元测试直接调用它;完整解读的敏感点表目前没有生产者写 `drekkana_22nd`(`_calc_sensitive_points` 只产 bhrigu_bindu 与 sarpa_drekkana),所以这一项目前不会出现在报告里。这是既有接线缺口,本单不接线,也不把「注册了」写成「已计算」。
|
||||
- 现象:结果取 D3 星座 +21。《Crux of Vedic Astrology》p.329:第 22 号 Drekkana 是 D3 的第 8 宫,即 +7。
|
||||
- 触发条件:调用 `calc_22nd_drekkana`。
|
||||
- 根因:把「在黄道上数 21 个十度分段」当成「在 D3 里移 21 个星座」。
|
||||
- 修复:改 `+7`;`offset_from_lagna_drekkana` 仍是 22,输出字段名不变。
|
||||
- 验证:`tests/test_upstream_sync9b_varga_bphs.py` 的固定反例(射手 D3 起,第 8 宫为巨蟹)与 36 段独立枚举(不调用生产偏移)通过;`tests/test_varga_bphs.py` 同步改成固定反例。密封 20 条 + 报时 900 条与上一份记录逐条相同。
|
||||
- 防复发:独立枚举测试用「数满 22 个十度分段再映射 D3」的旁路口径,不复用生产公式。
|
||||
- 关联:BUG-1494。
|
||||
- 复发自:无。
|
||||
- 修复版本:分支 `codex/upstream-sync9b-20261028`。
|
||||
|
||||
@@ -0,0 +1,118 @@
|
||||
{
|
||||
"record_version": "reported-offset-native-candidate-date-v3",
|
||||
"frozen_at_utc": "2026-10-28T08:19:09.924155+00:00",
|
||||
"ayanamsa": "raman",
|
||||
"node_mode": "mean",
|
||||
"radii_minutes": [
|
||||
15,
|
||||
30,
|
||||
60
|
||||
],
|
||||
"offsets_minutes": [
|
||||
-30,
|
||||
-20,
|
||||
-15,
|
||||
-10,
|
||||
-8,
|
||||
-5,
|
||||
-3,
|
||||
0,
|
||||
3,
|
||||
5,
|
||||
8,
|
||||
10,
|
||||
15,
|
||||
20,
|
||||
30
|
||||
],
|
||||
"minute_step": 1,
|
||||
"dataset": "references/real_case_calibration/minute_rectification_holdout_v3.json",
|
||||
"dataset_sha256": "45aa76ab79dfc6c6404b6252083e1aa5c7e2e2b7de811fc11042a8ad2da3f0ea",
|
||||
"dataset_benchmark_id": "minute_rectification_fact_ranker_v4_holdout_v3",
|
||||
"implementation_sha256": "b44505aa0034e486fcfc29c8611a9559333a97c1005f92e6a5356bd855122205",
|
||||
"implementation_sha256_prefix": "b44505aa0034e486",
|
||||
"historical_artifacts_manifest_sha256": "6102a26a840be207b5858b3a4c0509274468ae9071e86d308cbbac7371d6864e",
|
||||
"production_scoring_files": [
|
||||
"scripts/active_rectification_event_engine.py",
|
||||
"scripts/active_rectification_events.py",
|
||||
"scripts/ashtakavarga.py",
|
||||
"scripts/dasha_analyzer.py",
|
||||
"scripts/divisional_charts_extended.py",
|
||||
"scripts/domain_calculation_service.py",
|
||||
"scripts/functional_benefics.py",
|
||||
"scripts/jaimini.py",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py",
|
||||
"scripts/minute_rectification_feature_facts_v4.py",
|
||||
"scripts/narayana_dasha.py",
|
||||
"scripts/rectification/api_service.py",
|
||||
"scripts/rectification/candidate_contrast.py",
|
||||
"scripts/rectification/candidate_window.py",
|
||||
"scripts/rectification/case_holdout.py",
|
||||
"scripts/rectification/contracts.py",
|
||||
"scripts/rectification/dasha_transition_proximity.py",
|
||||
"scripts/rectification/decision_policy.py",
|
||||
"scripts/rectification/event_probes.py",
|
||||
"scripts/rectification/refinement_packet.py",
|
||||
"scripts/rectification/scoring_service.py",
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"production_scoring_sha256": "7a727418651321d1b9073588587050c4dc6292587748cf35734dd76cefb0effe",
|
||||
"research_files": [
|
||||
"scripts/research/reported_offset_sweep.py",
|
||||
"scripts/research/cluster_width_lib.py",
|
||||
"scripts/research/probe_supply_after_six.py",
|
||||
"scripts/research/sealed_holdout_rerun.py",
|
||||
"scripts/minute_rectification_blind_eval.py",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py",
|
||||
"scripts/minute_rectification_holdout_validator.py"
|
||||
],
|
||||
"research_implementation_sha256": "6fa0b0c335ac0cdc25ee887d432ae2f1f6487c665aed9665ad5cc0bc6ef0283b",
|
||||
"file_sha256": {
|
||||
"scripts/active_rectification_event_engine.py": "96c537d221a84680ddaaba74e3335162c44b5bbd9a60d10e69550a2095910d98",
|
||||
"scripts/active_rectification_events.py": "03e333ccf1103caf685dfe50fe890ab1793e945037085f50ce834a4a3b232222",
|
||||
"scripts/ashtakavarga.py": "c524da3f54b2ed9c080b78b33854854a0ca3d5d79b7e536bb1c3bc2be3e02852",
|
||||
"scripts/dasha_analyzer.py": "3949b96813217fe624899856afec9f0b787c4cb0fea3a9a0d961990dbd11943a",
|
||||
"scripts/divisional_charts_extended.py": "e9820e80f14fddc86ab5495d11455d16c2d3c9502a9a242fcf9efc41186e0d11",
|
||||
"scripts/domain_calculation_service.py": "66923a2bc69daf65c965d2973c4b9234edbec5147909eaf3609b6b377ce3c7ca",
|
||||
"scripts/functional_benefics.py": "cbaac3b8c09b97f8724b5300e9a402cbf77089af6c7db8788550d40fd35ac57b",
|
||||
"scripts/jaimini.py": "6b88658da5404da9b136686d92a04be462d61a39da6e8de4255021e2ed2d1173",
|
||||
"scripts/minute_rectification_blind_eval.py": "07aa30d8bad3278669495d5fea8be937aaf6367c8af980ff4f2fe9aa84ccc6ff",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py": "bdf460e3467208e8b87345c5beb2128f3e22de7eeffd68f72b281b3ad9affc92",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py": "f1a0d8d2482cd754d2e7f253a9606b0373519435a2bf58cfc3753e2b9ae0fb76",
|
||||
"scripts/minute_rectification_feature_facts_v4.py": "3d899a2cdd4825b8e32062443d487edcd2173a4ea55a36eb9f3abe587c0faf0f",
|
||||
"scripts/minute_rectification_holdout_validator.py": "b60b1c752e58672beaee8b36eb3b2348169726cda070ec969db0f13e7ed715af",
|
||||
"scripts/narayana_dasha.py": "bc667c30c9562fb73fb0b7b4c22a5e377f9a531795141fc629b2cd3cf396773a",
|
||||
"scripts/rectification/api_service.py": "089730097d3872a4f7b5d7dd5574bb7e9ab4d2e246d4a380800bc824d7979b95",
|
||||
"scripts/rectification/candidate_contrast.py": "eee7da71c0574a08876404b78ca111153fa95fb83ace82b9fdca141d1992e273",
|
||||
"scripts/rectification/candidate_window.py": "2fbc5058b12049b15fca375cdc125b8283e19f9f3e4bedcc291e344501891bef",
|
||||
"scripts/rectification/case_holdout.py": "fe0e699b617d9e216acdfeff87af4221c1d6f4c101bf33e1dbf14e2bcd75a8b5",
|
||||
"scripts/rectification/contracts.py": "c6dc6bd230e38f9f2126c224aae9ddbd6415304c15340f8c7cd3f06f6ef3160f",
|
||||
"scripts/rectification/dasha_transition_proximity.py": "5ce4ed27b0f06c681abc34e5fd998fafb10c153a0070aa36c99ddfa869a2cbf2",
|
||||
"scripts/rectification/decision_policy.py": "80e8de4680d19a052213bb821d2a9c94143a2962235aeb27f6ad81374d2e60d5",
|
||||
"scripts/rectification/event_probes.py": "f5ca9d54501f67a1546fcf5b01da0c1277dec2e2c6df481884e8900d14909a7c",
|
||||
"scripts/rectification/refinement_packet.py": "dbeea5aa780889785ce850f3881e8b7f67bb44594e9bc382c65b2e730884a2f4",
|
||||
"scripts/rectification/scoring_service.py": "fa056fa30d9e6ffa4b75295fc49c793e35b26ebeca64ca843d26c8abef3050f2",
|
||||
"scripts/research/cluster_width_lib.py": "1d8f2ffa7795d62069deebb2de8e16749317037d4ed3f24a2c0092676e5cfcc6",
|
||||
"scripts/research/probe_supply_after_six.py": "098a5b4398d6f8d996917d809c2fc922ad64031d3b70660f8ef7c876aba92438",
|
||||
"scripts/research/reported_offset_sweep.py": "8ecc381dfaa3c0e6bea058cfa44c606aabdb1086c137f16da82ee5a3bf5ccc91",
|
||||
"scripts/research/sealed_holdout_rerun.py": "ebcdae760f2b76c81d5d0c8e2bf347cff4c81cca9074f27ae94b6734408ccd42",
|
||||
"scripts/shadbala.py": "334dc9d8e4292f0c95d40fd4c29285aa89b9e49d4f187fb9498f4bb0ad93bdfc",
|
||||
"scripts/varga.py": "8ff96b9fc8346ca249abff6109434b6ed57fa150e1a9854d4f73bdf317568368"
|
||||
},
|
||||
"hash_scope": "explicit_identity_file_sets_not_a_transitive_dependency_lock",
|
||||
"scorer": "native_event_contribution_matrix_not_shadow_fact_ranker",
|
||||
"delivery": "initial_signature_clusters_peak_gap_lt_8_envelope_no_answers_no_elimination",
|
||||
"rank": "score_desc_then_sha256(benchmark_id:case_id:candidate_time)",
|
||||
"grid": "every_minute_inclusive_not_production_two_minute_sampling",
|
||||
"cross_midnight": "date_aware_candidates_distance_and_native_single_matrix",
|
||||
"evaluator_sha256": "8ecc381dfaa3c0e6bea058cfa44c606aabdb1086c137f16da82ee5a3bf5ccc91",
|
||||
"replay_revision": "native_candidate_date_v3",
|
||||
"supersedes": "candidate_date_grouped_v2_identity_and_path_not_assumed_numerically_wrong",
|
||||
"is_blind_evaluation": false,
|
||||
"truth_hidden_from_ranker": true,
|
||||
"official_valid_independent_blind": false,
|
||||
"official_blind_trial_count": 0,
|
||||
"results_previously_seen": true,
|
||||
"must_not_use_for_tuning": true
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,116 @@
|
||||
{
|
||||
"record_version": "exposed-v3-fixed-protocol-cross-midnight-rerun-v2",
|
||||
"extended_identity": {
|
||||
"historical_artifacts_manifest_sha256": "6102a26a840be207b5858b3a4c0509274468ae9071e86d308cbbac7371d6864e",
|
||||
"production_scoring_files": [
|
||||
"scripts/active_rectification_event_engine.py",
|
||||
"scripts/active_rectification_events.py",
|
||||
"scripts/ashtakavarga.py",
|
||||
"scripts/dasha_analyzer.py",
|
||||
"scripts/divisional_charts_extended.py",
|
||||
"scripts/domain_calculation_service.py",
|
||||
"scripts/functional_benefics.py",
|
||||
"scripts/jaimini.py",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py",
|
||||
"scripts/minute_rectification_feature_facts_v4.py",
|
||||
"scripts/narayana_dasha.py",
|
||||
"scripts/rectification/api_service.py",
|
||||
"scripts/rectification/candidate_contrast.py",
|
||||
"scripts/rectification/candidate_window.py",
|
||||
"scripts/rectification/case_holdout.py",
|
||||
"scripts/rectification/contracts.py",
|
||||
"scripts/rectification/dasha_transition_proximity.py",
|
||||
"scripts/rectification/decision_policy.py",
|
||||
"scripts/rectification/event_probes.py",
|
||||
"scripts/rectification/refinement_packet.py",
|
||||
"scripts/rectification/scoring_service.py",
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"production_scoring_sha256": "7a727418651321d1b9073588587050c4dc6292587748cf35734dd76cefb0effe",
|
||||
"research_files": [
|
||||
"scripts/research/reported_offset_sweep.py",
|
||||
"scripts/research/cluster_width_lib.py",
|
||||
"scripts/research/probe_supply_after_six.py",
|
||||
"scripts/research/sealed_holdout_rerun.py",
|
||||
"scripts/minute_rectification_blind_eval.py",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py",
|
||||
"scripts/minute_rectification_holdout_validator.py"
|
||||
],
|
||||
"research_implementation_sha256": "6fa0b0c335ac0cdc25ee887d432ae2f1f6487c665aed9665ad5cc0bc6ef0283b",
|
||||
"file_sha256": {
|
||||
"scripts/active_rectification_event_engine.py": "96c537d221a84680ddaaba74e3335162c44b5bbd9a60d10e69550a2095910d98",
|
||||
"scripts/active_rectification_events.py": "03e333ccf1103caf685dfe50fe890ab1793e945037085f50ce834a4a3b232222",
|
||||
"scripts/ashtakavarga.py": "c524da3f54b2ed9c080b78b33854854a0ca3d5d79b7e536bb1c3bc2be3e02852",
|
||||
"scripts/dasha_analyzer.py": "3949b96813217fe624899856afec9f0b787c4cb0fea3a9a0d961990dbd11943a",
|
||||
"scripts/divisional_charts_extended.py": "e9820e80f14fddc86ab5495d11455d16c2d3c9502a9a242fcf9efc41186e0d11",
|
||||
"scripts/domain_calculation_service.py": "66923a2bc69daf65c965d2973c4b9234edbec5147909eaf3609b6b377ce3c7ca",
|
||||
"scripts/functional_benefics.py": "cbaac3b8c09b97f8724b5300e9a402cbf77089af6c7db8788550d40fd35ac57b",
|
||||
"scripts/jaimini.py": "6b88658da5404da9b136686d92a04be462d61a39da6e8de4255021e2ed2d1173",
|
||||
"scripts/minute_rectification_blind_eval.py": "07aa30d8bad3278669495d5fea8be937aaf6367c8af980ff4f2fe9aa84ccc6ff",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py": "bdf460e3467208e8b87345c5beb2128f3e22de7eeffd68f72b281b3ad9affc92",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py": "f1a0d8d2482cd754d2e7f253a9606b0373519435a2bf58cfc3753e2b9ae0fb76",
|
||||
"scripts/minute_rectification_feature_facts_v4.py": "3d899a2cdd4825b8e32062443d487edcd2173a4ea55a36eb9f3abe587c0faf0f",
|
||||
"scripts/minute_rectification_holdout_validator.py": "b60b1c752e58672beaee8b36eb3b2348169726cda070ec969db0f13e7ed715af",
|
||||
"scripts/narayana_dasha.py": "bc667c30c9562fb73fb0b7b4c22a5e377f9a531795141fc629b2cd3cf396773a",
|
||||
"scripts/rectification/api_service.py": "089730097d3872a4f7b5d7dd5574bb7e9ab4d2e246d4a380800bc824d7979b95",
|
||||
"scripts/rectification/candidate_contrast.py": "eee7da71c0574a08876404b78ca111153fa95fb83ace82b9fdca141d1992e273",
|
||||
"scripts/rectification/candidate_window.py": "2fbc5058b12049b15fca375cdc125b8283e19f9f3e4bedcc291e344501891bef",
|
||||
"scripts/rectification/case_holdout.py": "fe0e699b617d9e216acdfeff87af4221c1d6f4c101bf33e1dbf14e2bcd75a8b5",
|
||||
"scripts/rectification/contracts.py": "c6dc6bd230e38f9f2126c224aae9ddbd6415304c15340f8c7cd3f06f6ef3160f",
|
||||
"scripts/rectification/dasha_transition_proximity.py": "5ce4ed27b0f06c681abc34e5fd998fafb10c153a0070aa36c99ddfa869a2cbf2",
|
||||
"scripts/rectification/decision_policy.py": "80e8de4680d19a052213bb821d2a9c94143a2962235aeb27f6ad81374d2e60d5",
|
||||
"scripts/rectification/event_probes.py": "f5ca9d54501f67a1546fcf5b01da0c1277dec2e2c6df481884e8900d14909a7c",
|
||||
"scripts/rectification/refinement_packet.py": "dbeea5aa780889785ce850f3881e8b7f67bb44594e9bc382c65b2e730884a2f4",
|
||||
"scripts/rectification/scoring_service.py": "fa056fa30d9e6ffa4b75295fc49c793e35b26ebeca64ca843d26c8abef3050f2",
|
||||
"scripts/research/cluster_width_lib.py": "1d8f2ffa7795d62069deebb2de8e16749317037d4ed3f24a2c0092676e5cfcc6",
|
||||
"scripts/research/probe_supply_after_six.py": "098a5b4398d6f8d996917d809c2fc922ad64031d3b70660f8ef7c876aba92438",
|
||||
"scripts/research/reported_offset_sweep.py": "8ecc381dfaa3c0e6bea058cfa44c606aabdb1086c137f16da82ee5a3bf5ccc91",
|
||||
"scripts/research/sealed_holdout_rerun.py": "ebcdae760f2b76c81d5d0c8e2bf347cff4c81cca9074f27ae94b6734408ccd42",
|
||||
"scripts/shadbala.py": "334dc9d8e4292f0c95d40fd4c29285aa89b9e49d4f187fb9498f4bb0ad93bdfc",
|
||||
"scripts/varga.py": "8ff96b9fc8346ca249abff6109434b6ed57fa150e1a9854d4f73bdf317568368"
|
||||
},
|
||||
"hash_scope": "explicit_identity_file_sets_not_a_transitive_dependency_lock"
|
||||
},
|
||||
"production_identity_scope": "context_only_shadow_scorer_does_not_call_transition_proximity",
|
||||
"frozen_at_utc": "2026-10-28T08:19:06.008600+00:00",
|
||||
"dataset_path": "references/real_case_calibration/minute_rectification_holdout_v3.json",
|
||||
"dataset_sha256": "45aa76ab79dfc6c6404b6252083e1aa5c7e2e2b7de811fc11042a8ad2da3f0ea",
|
||||
"algorithm_version": "birth-time-event-fact-ranker-v4-shadow",
|
||||
"implementation_sha256": "b44505aa0034e486fcfc29c8611a9559333a97c1005f92e6a5356bd855122205",
|
||||
"files": [
|
||||
"scripts/active_rectification_event_engine.py",
|
||||
"scripts/active_rectification_events.py",
|
||||
"scripts/ashtakavarga.py",
|
||||
"scripts/dasha_analyzer.py",
|
||||
"scripts/divisional_charts_extended.py",
|
||||
"scripts/domain_calculation_service.py",
|
||||
"scripts/jaimini.py",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py",
|
||||
"scripts/minute_rectification_feature_facts_v4.py",
|
||||
"scripts/narayana_dasha.py",
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"historical_frozen_sha256": "f41c298dd6cdcebe7a93e632f7191954be7987f6012ca2a34cecb6e447fbf196",
|
||||
"evaluator_sha256": "ebcdae760f2b76c81d5d0c8e2bf347cff4c81cca9074f27ae94b6734408ccd42",
|
||||
"ayanamsa": "raman",
|
||||
"node_mode": "mean",
|
||||
"candidate_radius_minutes": [
|
||||
10
|
||||
],
|
||||
"minute_step": 1,
|
||||
"release_metrics": {
|
||||
"top_1_rate_minimum": 0.6,
|
||||
"top_3_rate_minimum": 0.85,
|
||||
"mean_absolute_minute_error_maximum": 2.0,
|
||||
"false_confirmation_rate_maximum": 0.05,
|
||||
"correct_insufficient_evidence_rejection_rate_minimum": 0.9
|
||||
},
|
||||
"results_previously_seen": true,
|
||||
"official_valid_independent_blind": false,
|
||||
"must_not_use_for_tuning": true,
|
||||
"tie_breaker": "sha256(benchmark_id:case_id:candidate_time); published minute is never passed to the ranker",
|
||||
"metric_rank_definition": "competition_rank_1_plus_strictly_higher_scores_legacy_protocol",
|
||||
"extra_metric_rank_definition": "score_desc_then_existing_opaque_sha256_total_order"
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,45 @@
|
||||
# 22nd Drekkana: division count versus D3 house count
|
||||
|
||||
## Source
|
||||
|
||||
- `references/book_corpus/books/Crux of Vedic Astrology – Timing of Events (Sanjay Rath) (z-library.sk, 1lib.sk, z-lib.sk).md`
|
||||
- Topic: 22nd Drekkana geometry. Corpus page 340, printed page 329.
|
||||
- Lines 13809–13812: `house on the physical body. Incidentally, the 22nd`
|
||||
`decanate is also the 8th house in the Drekkana`
|
||||
`(D-3) chart while the 64th Navamsa is the 4th`
|
||||
`house from the Moon in the Navamsa chart. The`
|
||||
- Located by full-corpus search and read using `search_jyotish_books.py --read-unit 340`.
|
||||
- This review verifies a traditional geometric definition, not health or lifespan prediction.
|
||||
|
||||
## Defect and correction
|
||||
|
||||
The producer added 21 to the D3 sign index. That confuses a count of zodiacal
|
||||
ten-degree divisions with a count of signs in the divisional chart. Use D3
|
||||
ascendant +7 modulo12, the eighth house inclusive.
|
||||
|
||||
The old test repeated the same +21 error. Replace it with a fixed Sagittarius
|
||||
to Cancer counterexample and an independent 36-part zodiac enumeration. Across
|
||||
each part, count 22 inclusively on the original zodiac, then apply the standard
|
||||
Parashari D3 mapping to the resulting part. Test starts, interiors and ends.
|
||||
|
||||
The 64th Navamsa formula is unchanged: D9 Moon +63 modulo12 equals its fourth
|
||||
house, as the same source states. `offset_from_lagna_drekkana=22` is an ordinal
|
||||
label, not the number of D3 signs added.
|
||||
|
||||
No customer information is retained here. Recompute sensitive-point consumers
|
||||
and use a new verified frozen pin before claiming the published report changed.
|
||||
|
||||
## Sarpa classification: missing two divisions
|
||||
|
||||
Raman, `Hindu Predictive Astrology -- Bangalore Venkat Raman, B V Raman -- 1981 -- IBH Prakashana -- isbn13 9788119394883 -- c9102b89e2f8f7c358a913f7d07d7c39 -- Anna’s Archive.md`:
|
||||
|
||||
- Corpus p.279, L10960–10962 explicitly counts five serpent divisions.
|
||||
- Cancer second and third: p.280, L11013–11020.
|
||||
- Scorpio first and second: pp.281–282, L11062–11074.
|
||||
- Pisces third: p.283, L11129–11131.
|
||||
- Search used `search_jyotish_books.py serpent --book <registered filename>`.
|
||||
|
||||
The old map accepted one division per sign and omitted Cancer-3 and Scorpio-2.
|
||||
It now allows multiple divisions per sign. Independent tests cover all 36
|
||||
divisions and their boundaries against the source's three degree intervals.
|
||||
This classifies chart geometry; it does not establish a medical outcome.
|
||||
@@ -0,0 +1,60 @@
|
||||
# PROGRESS · 上游同步第九轮乙批(2026-10-28)
|
||||
|
||||
- 分支:`codex/upstream-sync9b-20261028`;基线 `origin/staging` `12eb7018`
|
||||
- issue:#159(#141 乙批);产品 10-28 选 **A**:允许改冻结文件 `scripts/varga.py`
|
||||
- 上游:`732642856/yinduzhanxing` main `50847e57`(10-16),按语义移植
|
||||
- 结论:B1 两项完成;密封校正 20 条与报时窗口 900 条与上一份记录逐条相同,已按 ERR-110 另存新冻结;B2(Narayana 小运强度口径)按决策记录不做
|
||||
|
||||
## 做了什么
|
||||
|
||||
| 项 | 上游 | BUG | 改了什么 |
|
||||
| --- | --- | --- | --- |
|
||||
| T1 Sarpa 五段 + 原始经度判段 | `50847e57` | BUG-1494 | `SARPA_DREKKANA_SIGNS` 由单段号改段号元组;`calc_sarpa_drekkana` 去掉四舍五入、先取模;`definition` 改五段 |
|
||||
| T2 第 22 号 Drekkana 改 D3 第 8 宫 | `50847e57` | BUG-1495 | `calc_22nd_drekkana` 由 `+21` 改 `+7`,字段名与序号 22 不变 |
|
||||
| T4 上游配套文档 | `50847e57` | — | 原路径放入 `docs/research/sensitive_point_drekkana_count_review_2026_10_14.md` |
|
||||
| T3 重新冻结 | — | — | 两份新冻结记录 + 两份回放报告(ERR-110),旧记录逐字节保留 |
|
||||
|
||||
生产文件只有 `scripts/varga.py` 一个;`git diff --stat` 见下。
|
||||
|
||||
## 与任务书的偏离
|
||||
|
||||
1. **红线 2 的「先不带 `--freeze` 跑」做不到**:`scripts/varga.py` 在冻结记录的扩展身份里,拿 sync8 的冻结记录回放会在打分前被身份闸门拦下(`frozen_record_mismatch:extended_identity`)。改成 ERR-110 的做法:仓库内建临时冻结记录 → 回放 → 与 sync8 逐条比 → 全部相同后才写正式记录。临时记录 `docs/research/.tmp_sweep_sync9b.freeze.json` 用完已删除,未提交。
|
||||
2. **报时窗口脚本必须用仓库内路径**:报告里写 `freeze_record_path`(`relative_to(ROOT)`),所以正式记录直接放 `docs/research/`;比较轮的临时记录也在仓库内。
|
||||
3. **改了前端一个测试文件**:`frontend/tests/rectification-confirmation-gate.test.ts` 写死当前密封报告路径,合同指针一挪就会红。只改这个路径与三栏注释,不动任何产品代码;与第八轮同做法的先例一致。
|
||||
|
||||
## 跑过的命令
|
||||
|
||||
| 检查 | 命令 | 结果 |
|
||||
| --- | --- | --- |
|
||||
| 上游两个测试文件 | `.venv\Scripts\python -m pytest tests/test_upstream_sync9b_varga_bphs.py tests/test_upstream_sync9b_sarpa_precision.py -o addopts="" -q` | 23 passed |
|
||||
| 既有分盘测试一起 | 上一行再加 `tests/test_varga_bphs.py` | 39 passed |
|
||||
| CLI 敏感点(任务书写 `-k "sarpa or drekkana or special"`) | `.venv\Scripts\python -m pytest tests/test_cli_smoke.py -k "sarpa or drekkana or special"` | 0 条被选中(35 deselected,退出码 5);`-k` 只匹配测试名,改用实际测试名 `-k sensitive_point_modules`:1 passed、34 deselected |
|
||||
| 分盘 + CLI 敏感点合并 | 4 个文件/节点一起跑 | 40 passed |
|
||||
| 密封校正 20 条 | `scripts/research/sealed_holdout_rerun.py`(新冻结记录) | `trial_count` 20;8 个字段(`true_rank`、`opaque_true_rank`、`minute_error`、`would_confirm`、`false_confirmation`、`insufficient_evidence_rejected`、`candidate_count`、`event_count`)不一致 0;`metrics` 相同;`changed_trial_count` 仍是 8 |
|
||||
| 报时窗口 900 条 | `scripts/research/reported_offset_sweep.py --json`(新冻结记录) | `trial_count` 900;trial 全字段不一致 0;`summary` 与 `widening_geometry` 相同;`changed_trial_count` 仍是 581 |
|
||||
| 冻结契约 | `tests/test_sealed_holdout_contract_freshness.py` | 9 passed |
|
||||
| 确认门合同 | `tests/test_rectification_confirmation_and.py` | 10 passed |
|
||||
| 其余分盘测试 | `pytest tests/test_varga*.py` | 53 passed、9 failed;9 条全在 `test_varga_vedastro_mode.py`(D2 起 Ascendant 星座不符)。在基线 `12eb7018` 的一次性工作树上同样 9 failed,与 Sarpa / 22nd 无关,不算本单 |
|
||||
| 正式记录生成 | `scripts/research/*.py --freeze` 两份 + 回放两份 | `sealed_holdout_rerun_upstream_sync9b_2026_10_28.{freeze.json,json}`、`reported_offset_upstream_sync9b_2026_10_28.{freeze.json,json}` |
|
||||
|
||||
Python 快速门、前端 tsc / lint / build、`npm test`、`test:db` 没跑:没有改前端产品代码,没有动表。
|
||||
|
||||
## 断言三栏
|
||||
|
||||
| 位置 | 原值 | 新值 | 原因 |
|
||||
| --- | --- | --- | --- |
|
||||
| `tests/test_varga_bphs.py::test_22nd_drekkana_counts_forward_from_lagna_drekkana` | `expected = (drekkana_ref(asc_lon) + 21) % 12` | 固定 `3`(巨蟹),保留 `offset_from_lagna_drekkana == 22` | 旧断言把「+21」的错口径抄进了测试;换成书上的固定反例(射手 D3 起,第 8 宫为巨蟹) |
|
||||
| `tests/test_cli_smoke.py::test_full_reading_exposes_sensitive_point_modules` | `definition == "Cancer-2, Scorpio-1, Pisces-3"` | `definition == "Cancer-2, Cancer-3, Scorpio-1, Scorpio-2, Pisces-3"` | BUG-1494 改的就是这个定义字符串;仍逐字比对,没有放宽 |
|
||||
| `tests/test_sealed_holdout_contract_freshness.py` 排除前缀 | 排除到 `upstream_sync8_2026_10_18` | 增加 `upstream_sync9b_2026_10_28` 两条 | ERR-110 另存新冻结,旧记录留在清单外 |
|
||||
| `frontend/tests/rectification-confirmation-gate.test.ts` 读取与断言路径 | `…upstream_sync8_2026_10_18.json` | `…upstream_sync9b_2026_10_28.json` | 合同当前指针移到新报告;注释补第 11 条三栏 |
|
||||
| `scripts/research/sealed_holdout_rerun.py`、`reported_offset_sweep.py` 的 `FREEZE` / `REPORT` | `…upstream_sync8_2026_10_18` | `…upstream_sync9b_2026_10_28` | 同上,ERR-110 |
|
||||
|
||||
## 发现但没改
|
||||
|
||||
- 完整解读的敏感点表没有 `drekkana_22nd` 的生产者:`_calc_sensitive_points` 只产 `bhrigu_bindu` 与 `sarpa_drekkana`。所以第 22 号 Drekkana 修好后,报告里暂时看不到变化;这是既有接线缺口,本单不接线(也不把「有函数」写成「报告里已计算」)。
|
||||
- `frontend/tests/fixtures/report-density-fictional-engine.json` 里还有两处旧 `definition` 字符串。它是前端 fixture,本单不改前端产品代码,留给前端轮次或验收方判断。
|
||||
|
||||
## 环境缺口
|
||||
|
||||
- Windows 跑 Python 测试要 `PYTHONUTF8=1`,否则子进程按 GBK 编码,遇到警告符号会 `UnicodeEncodeError`,看起来像引擎崩了。
|
||||
- 前端测试没跑(任务书不要求,且本单没改前端产品代码)。
|
||||
@@ -544,4 +544,4 @@
|
||||
| — | `PROGRESS-session-shell-116-20261028.md` | **#116 侧栏会话菜单搬进外壳**:每个页面都能「…」和拖动(直接执行,BUG-1467) | 已推 staging | `codex/session-shell-116-20261027` |
|
||||
| `TASK-home-crash-saved-people-20261027.md` | `PROGRESS-home-crash-saved-people-20261027.md` | **#115 首页崩溃**:存过别人的账户一进首页就「页面出错了」——人物列表的资料缺两个字段,启程引导一读就报错;入口补齐默认值(BUG-1464) | 待验收 | `codex/home-crash-saved-people-20261027` |
|
||||
| `TASK-upstream-sync9-20261028.md` | `PROGRESS-upstream-sync9-20261028.md` | **第 1 次打回(快速门 1 败:Darakaraka 旧测试锁错值,见 `TASK-upstream-sync9-fix-20261028.md`)** · **#141 上游同步第九轮**:甲批九项已做完并推 `codex/upstream-sync9-20261028`;校正 20 条和 900 条与上一份回放逐条相同;乙批仍等 #137 | 待验收 | `codex/upstream-sync9-20261028` |
|
||||
| `TASK-upstream-sync9b-20261028.md` | — | **#159 上游同步第九轮乙批(产品选 A)**:Sarpa Drekkana 补成五段、第 22 号 Drekkana 改为 D3 第 8 宫;改冻结文件 `varga.py`,校正 20 + 900 分数逐条相同才重新冻结。Narayana 小运强度口径(B2)不做,另问产品 | 待领取 | `codex/upstream-sync9b-20261028` |
|
||||
| `TASK-upstream-sync9b-20261028.md` | `PROGRESS-upstream-sync9b-20261028.md` | **#159 上游同步第九轮乙批(产品选 A)**:Sarpa Drekkana 补成五段、第 22 号 Drekkana 改为 D3 第 8 宫;改冻结文件 `varga.py`,校正 20 + 900 与上一份逐条相同后按 ERR-110 重新冻结。Narayana 小运强度口径(B2)不做,另问产品 | 待验收 | `codex/upstream-sync9b-20261028` |
|
||||
|
||||
@@ -111,8 +111,11 @@ const diagnosticReport = JSON.parse(readFileSync(
|
||||
// 原值(10):docs/research/sealed_holdout_rerun_scoring_perf_2026_10_13.json
|
||||
// 新值(10):docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json
|
||||
// 原因(10):sync8(BUG-1380~1390)改了冻结身份文件,输出不变,ERR-110 另存新记录。确认门行为与阈值不变。
|
||||
// 原值(11):docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json
|
||||
// 新值(11):docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json
|
||||
// 原因(11):sync9b(BUG-1494~1495)改了冻结身份里的 scripts/varga.py,输出不变,ERR-110 另存新记录。确认门行为与阈值不变。
|
||||
const currentTreeRerun = JSON.parse(readFileSync(
|
||||
new URL("../../docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json", import.meta.url),
|
||||
new URL("../../docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json", import.meta.url),
|
||||
"utf8",
|
||||
)) as {
|
||||
frozen_record: { implementation_sha256: string };
|
||||
@@ -260,9 +263,10 @@ test("sealed holdout aggregates match the v3 report and still block confirmation
|
||||
// 原值(7):…upstream_sync6_2026_10_07.json / 新值(7):…ephemeris_nutation_2026_10_08.json / 原因(7):章动修正与 scoring-12 重新冻结(ERR-110,BUG-1275)。
|
||||
// 原值(8):…ephemeris_nutation_2026_10_08.json / 新值(8):…scoring_perf_2026_10_13.json / 原因(8):BUG-1323~1325 改了冻结身份文件,输出不变,ERR-110 另存新记录。
|
||||
// 原值(9):…scoring_perf_2026_10_13.json / 新值(9):…upstream_sync8_2026_10_18.json / 原因(9):sync8 改了冻结身份文件,输出不变,ERR-110 另存新记录。
|
||||
// 原值(10):…upstream_sync8_2026_10_18.json / 新值(10):…upstream_sync9b_2026_10_28.json / 原因(10):sync9b 改了冻结身份里的 varga.py,输出不变,ERR-110 另存新记录。
|
||||
assert.equal(
|
||||
productHoldout.current_tree_scorer.source_report,
|
||||
"docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json",
|
||||
"docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json",
|
||||
);
|
||||
assert.equal(currentTreeRerun.official_valid_independent_blind, false);
|
||||
assert.equal(productHoldout.current_tree_scorer.matches_metrics_scorer, false);
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
"dataset_path": "references/real_case_calibration/minute_rectification_holdout_v3.json",
|
||||
"report_path": "references/real_case_calibration/minute_rectification_holdout_v3_report.json",
|
||||
"source_audit_status": "corrected_known_date_errors",
|
||||
"evaluated_on": "2026-10-18",
|
||||
"evaluated_on": "2026-10-28",
|
||||
"evaluated_on_scope": "latest_fixed_protocol_rerun_not_historical_runtime_metrics",
|
||||
"historical_source_audit_status": "invalidated_after_replay",
|
||||
"report_status": "invalidated_after_source_audit",
|
||||
@@ -24,7 +24,7 @@
|
||||
"evaluated_on": "2026-07-21"
|
||||
},
|
||||
"current_tree_scorer": {
|
||||
"implementation_sha256": "bf8981b5c41702f9b333444deee2ab7378b9e98b111240e85ea62e6aae02fda8",
|
||||
"implementation_sha256": "b44505aa0034e486fcfc29c8611a9559333a97c1005f92e6a5356bd855122205",
|
||||
"extended_identity": {
|
||||
"historical_artifacts_manifest_sha256": "6102a26a840be207b5858b3a4c0509274468ae9071e86d308cbbac7371d6864e",
|
||||
"production_scoring_files": [
|
||||
@@ -52,7 +52,7 @@
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"production_scoring_sha256": "c2c23bcbde5de58e519ae1d6545620edd0f738ce8dc2e872e659b598137a728f",
|
||||
"production_scoring_sha256": "7a727418651321d1b9073588587050c4dc6292587748cf35734dd76cefb0effe",
|
||||
"research_files": [
|
||||
"scripts/research/reported_offset_sweep.py",
|
||||
"scripts/research/cluster_width_lib.py",
|
||||
@@ -62,7 +62,7 @@
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py",
|
||||
"scripts/minute_rectification_holdout_validator.py"
|
||||
],
|
||||
"research_implementation_sha256": "9df579bdacd7dec43abd92c9abc1831771feb800fc29e6864dc315d083d52a03",
|
||||
"research_implementation_sha256": "6fa0b0c335ac0cdc25ee887d432ae2f1f6487c665aed9665ad5cc0bc6ef0283b",
|
||||
"file_sha256": {
|
||||
"scripts/active_rectification_event_engine.py": "96c537d221a84680ddaaba74e3335162c44b5bbd9a60d10e69550a2095910d98",
|
||||
"scripts/active_rectification_events.py": "03e333ccf1103caf685dfe50fe890ab1793e945037085f50ce834a4a3b232222",
|
||||
@@ -90,17 +90,17 @@
|
||||
"scripts/rectification/scoring_service.py": "fa056fa30d9e6ffa4b75295fc49c793e35b26ebeca64ca843d26c8abef3050f2",
|
||||
"scripts/research/cluster_width_lib.py": "1d8f2ffa7795d62069deebb2de8e16749317037d4ed3f24a2c0092676e5cfcc6",
|
||||
"scripts/research/probe_supply_after_six.py": "098a5b4398d6f8d996917d809c2fc922ad64031d3b70660f8ef7c876aba92438",
|
||||
"scripts/research/reported_offset_sweep.py": "e10537ca2caba3a4e6a8d2460265543b0cca55935afa8004108e45bef4bc3de7",
|
||||
"scripts/research/sealed_holdout_rerun.py": "7945353014b93b6d7641f278779111d85b1773293781343b802a9b4b655ca4b5",
|
||||
"scripts/research/reported_offset_sweep.py": "8ecc381dfaa3c0e6bea058cfa44c606aabdb1086c137f16da82ee5a3bf5ccc91",
|
||||
"scripts/research/sealed_holdout_rerun.py": "ebcdae760f2b76c81d5d0c8e2bf347cff4c81cca9074f27ae94b6734408ccd42",
|
||||
"scripts/shadbala.py": "334dc9d8e4292f0c95d40fd4c29285aa89b9e49d4f187fb9498f4bb0ad93bdfc",
|
||||
"scripts/varga.py": "c1f06967c3d4d214edadff139c24aa31e59fb628477174235abe14f799a99076"
|
||||
"scripts/varga.py": "8ff96b9fc8346ca249abff6109434b6ed57fa150e1a9854d4f73bdf317568368"
|
||||
},
|
||||
"hash_scope": "explicit_identity_file_sets_not_a_transitive_dependency_lock"
|
||||
},
|
||||
"matches_metrics_scorer": false,
|
||||
"official_eval_implementation_hash_matches": false,
|
||||
"official_eval_trial_count": 0,
|
||||
"source_report": "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json",
|
||||
"source_report": "docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json",
|
||||
"fixed_protocol_rerun_trial_count": 20,
|
||||
"fixed_protocol_rerun_hash_matches": true,
|
||||
"metrics": {
|
||||
@@ -113,6 +113,106 @@
|
||||
}
|
||||
},
|
||||
"current_tree_fixed_protocol_rerun": {
|
||||
"evaluated_on": "2026-10-28",
|
||||
"report_path": "docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json",
|
||||
"freeze_record_path": "docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.freeze.json",
|
||||
"implementation_sha256": "b44505aa0034e486fcfc29c8611a9559333a97c1005f92e6a5356bd855122205",
|
||||
"extended_identity": {
|
||||
"historical_artifacts_manifest_sha256": "6102a26a840be207b5858b3a4c0509274468ae9071e86d308cbbac7371d6864e",
|
||||
"production_scoring_files": [
|
||||
"scripts/active_rectification_event_engine.py",
|
||||
"scripts/active_rectification_events.py",
|
||||
"scripts/ashtakavarga.py",
|
||||
"scripts/dasha_analyzer.py",
|
||||
"scripts/divisional_charts_extended.py",
|
||||
"scripts/domain_calculation_service.py",
|
||||
"scripts/functional_benefics.py",
|
||||
"scripts/jaimini.py",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py",
|
||||
"scripts/minute_rectification_feature_facts_v4.py",
|
||||
"scripts/narayana_dasha.py",
|
||||
"scripts/rectification/api_service.py",
|
||||
"scripts/rectification/candidate_contrast.py",
|
||||
"scripts/rectification/candidate_window.py",
|
||||
"scripts/rectification/case_holdout.py",
|
||||
"scripts/rectification/contracts.py",
|
||||
"scripts/rectification/dasha_transition_proximity.py",
|
||||
"scripts/rectification/decision_policy.py",
|
||||
"scripts/rectification/event_probes.py",
|
||||
"scripts/rectification/refinement_packet.py",
|
||||
"scripts/rectification/scoring_service.py",
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"production_scoring_sha256": "7a727418651321d1b9073588587050c4dc6292587748cf35734dd76cefb0effe",
|
||||
"research_files": [
|
||||
"scripts/research/reported_offset_sweep.py",
|
||||
"scripts/research/cluster_width_lib.py",
|
||||
"scripts/research/probe_supply_after_six.py",
|
||||
"scripts/research/sealed_holdout_rerun.py",
|
||||
"scripts/minute_rectification_blind_eval.py",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py",
|
||||
"scripts/minute_rectification_holdout_validator.py"
|
||||
],
|
||||
"research_implementation_sha256": "6fa0b0c335ac0cdc25ee887d432ae2f1f6487c665aed9665ad5cc0bc6ef0283b",
|
||||
"file_sha256": {
|
||||
"scripts/active_rectification_event_engine.py": "96c537d221a84680ddaaba74e3335162c44b5bbd9a60d10e69550a2095910d98",
|
||||
"scripts/active_rectification_events.py": "03e333ccf1103caf685dfe50fe890ab1793e945037085f50ce834a4a3b232222",
|
||||
"scripts/ashtakavarga.py": "c524da3f54b2ed9c080b78b33854854a0ca3d5d79b7e536bb1c3bc2be3e02852",
|
||||
"scripts/dasha_analyzer.py": "3949b96813217fe624899856afec9f0b787c4cb0fea3a9a0d961990dbd11943a",
|
||||
"scripts/divisional_charts_extended.py": "e9820e80f14fddc86ab5495d11455d16c2d3c9502a9a242fcf9efc41186e0d11",
|
||||
"scripts/domain_calculation_service.py": "66923a2bc69daf65c965d2973c4b9234edbec5147909eaf3609b6b377ce3c7ca",
|
||||
"scripts/functional_benefics.py": "cbaac3b8c09b97f8724b5300e9a402cbf77089af6c7db8788550d40fd35ac57b",
|
||||
"scripts/jaimini.py": "6b88658da5404da9b136686d92a04be462d61a39da6e8de4255021e2ed2d1173",
|
||||
"scripts/minute_rectification_blind_eval.py": "07aa30d8bad3278669495d5fea8be937aaf6367c8af980ff4f2fe9aa84ccc6ff",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py": "bdf460e3467208e8b87345c5beb2128f3e22de7eeffd68f72b281b3ad9affc92",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py": "f1a0d8d2482cd754d2e7f253a9606b0373519435a2bf58cfc3753e2b9ae0fb76",
|
||||
"scripts/minute_rectification_feature_facts_v4.py": "3d899a2cdd4825b8e32062443d487edcd2173a4ea55a36eb9f3abe587c0faf0f",
|
||||
"scripts/minute_rectification_holdout_validator.py": "b60b1c752e58672beaee8b36eb3b2348169726cda070ec969db0f13e7ed715af",
|
||||
"scripts/narayana_dasha.py": "bc667c30c9562fb73fb0b7b4c22a5e377f9a531795141fc629b2cd3cf396773a",
|
||||
"scripts/rectification/api_service.py": "089730097d3872a4f7b5d7dd5574bb7e9ab4d2e246d4a380800bc824d7979b95",
|
||||
"scripts/rectification/candidate_contrast.py": "eee7da71c0574a08876404b78ca111153fa95fb83ace82b9fdca141d1992e273",
|
||||
"scripts/rectification/candidate_window.py": "2fbc5058b12049b15fca375cdc125b8283e19f9f3e4bedcc291e344501891bef",
|
||||
"scripts/rectification/case_holdout.py": "fe0e699b617d9e216acdfeff87af4221c1d6f4c101bf33e1dbf14e2bcd75a8b5",
|
||||
"scripts/rectification/contracts.py": "c6dc6bd230e38f9f2126c224aae9ddbd6415304c15340f8c7cd3f06f6ef3160f",
|
||||
"scripts/rectification/dasha_transition_proximity.py": "5ce4ed27b0f06c681abc34e5fd998fafb10c153a0070aa36c99ddfa869a2cbf2",
|
||||
"scripts/rectification/decision_policy.py": "80e8de4680d19a052213bb821d2a9c94143a2962235aeb27f6ad81374d2e60d5",
|
||||
"scripts/rectification/event_probes.py": "f5ca9d54501f67a1546fcf5b01da0c1277dec2e2c6df481884e8900d14909a7c",
|
||||
"scripts/rectification/refinement_packet.py": "dbeea5aa780889785ce850f3881e8b7f67bb44594e9bc382c65b2e730884a2f4",
|
||||
"scripts/rectification/scoring_service.py": "fa056fa30d9e6ffa4b75295fc49c793e35b26ebeca64ca843d26c8abef3050f2",
|
||||
"scripts/research/cluster_width_lib.py": "1d8f2ffa7795d62069deebb2de8e16749317037d4ed3f24a2c0092676e5cfcc6",
|
||||
"scripts/research/probe_supply_after_six.py": "098a5b4398d6f8d996917d809c2fc922ad64031d3b70660f8ef7c876aba92438",
|
||||
"scripts/research/reported_offset_sweep.py": "8ecc381dfaa3c0e6bea058cfa44c606aabdb1086c137f16da82ee5a3bf5ccc91",
|
||||
"scripts/research/sealed_holdout_rerun.py": "ebcdae760f2b76c81d5d0c8e2bf347cff4c81cca9074f27ae94b6734408ccd42",
|
||||
"scripts/shadbala.py": "334dc9d8e4292f0c95d40fd4c29285aa89b9e49d4f187fb9498f4bb0ad93bdfc",
|
||||
"scripts/varga.py": "8ff96b9fc8346ca249abff6109434b6ed57fa150e1a9854d4f73bdf317568368"
|
||||
},
|
||||
"hash_scope": "explicit_identity_file_sets_not_a_transitive_dependency_lock"
|
||||
},
|
||||
"scorer_frozen_before_rerun": true,
|
||||
"source_audit_status": "corrected_known_date_errors",
|
||||
"trial_count": 20,
|
||||
"official_valid_independent_blind": false,
|
||||
"is_blind_evaluation": false,
|
||||
"truth_hidden_from_ranker": true,
|
||||
"results_previously_seen": true,
|
||||
"must_not_claim_as_release_metrics": true,
|
||||
"must_not_use_for_tuning": true,
|
||||
"verified_minute_claim_allowed": false,
|
||||
"metric_gates_passed": false,
|
||||
"events_per_case": 3,
|
||||
"boundary": "Previously exposed v3 shadow fixed-protocol rerun after upstream sync9b (ERR-110, BUG-1494 to BUG-1495). Trials and metrics match the 2026-10-18 upstream sync8 report. Versus the 2026-09-20 historical report, changed_trial_count stays 8. Not a release metric. Prior sync8 report and freeze preserved byte-for-byte.",
|
||||
"report_sha256": "ef20e751a746a4ec3b368d6860123602172a9af9195a97ec5f4d3c2cdf4823ce",
|
||||
"freeze_record_sha256": "32cad06f25c84891a24725110c9737489b8d79ed7c2d33ae959cb8eb16798dab",
|
||||
"replay_started_at_utc": "2026-10-28T08:19:06.261911+00:00",
|
||||
"replay_finished_at_utc": "2026-10-28T08:19:09.621910+00:00",
|
||||
"previous_fixed_protocol_rerun": {
|
||||
"report_path": "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json",
|
||||
"freeze_record_path": "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.freeze.json",
|
||||
"superseded_reason": "Upstream sync9b (BUG-1494 to BUG-1495) changed scripts/varga.py, which is part of the extended identity. Output is unchanged, so ERR-110 stored a new record. Prior sync8 report and freeze preserved byte-for-byte."
|
||||
}
|
||||
},
|
||||
"previous_fixed_protocol_rerun": {
|
||||
"evaluated_on": "2026-10-18",
|
||||
"report_path": "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json",
|
||||
"freeze_record_path": "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.freeze.json",
|
||||
@@ -212,106 +312,6 @@
|
||||
"superseded_reason": "Upstream sync8 (BUG-1380 to BUG-1390) changed frozen identity files. Output is unchanged, so ERR-110 stored a new record. Prior scoring_perf report and freeze preserved byte-for-byte."
|
||||
}
|
||||
},
|
||||
"previous_fixed_protocol_rerun": {
|
||||
"evaluated_on": "2026-10-03",
|
||||
"report_path": "docs/research/sealed_holdout_rerun_astrologer_rulings_batch1_2026_10_03.json",
|
||||
"freeze_record_path": "docs/research/sealed_holdout_rerun_astrologer_rulings_batch1_2026_10_03.freeze.json",
|
||||
"implementation_sha256": "114c60c45fa35a77bb6bfe2c177bbcc90b2e0748e2a33e61975f7393802f96f2",
|
||||
"extended_identity": {
|
||||
"historical_artifacts_manifest_sha256": "6102a26a840be207b5858b3a4c0509274468ae9071e86d308cbbac7371d6864e",
|
||||
"production_scoring_files": [
|
||||
"scripts/active_rectification_event_engine.py",
|
||||
"scripts/active_rectification_events.py",
|
||||
"scripts/ashtakavarga.py",
|
||||
"scripts/dasha_analyzer.py",
|
||||
"scripts/divisional_charts_extended.py",
|
||||
"scripts/domain_calculation_service.py",
|
||||
"scripts/functional_benefics.py",
|
||||
"scripts/jaimini.py",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py",
|
||||
"scripts/minute_rectification_feature_facts_v4.py",
|
||||
"scripts/narayana_dasha.py",
|
||||
"scripts/rectification/api_service.py",
|
||||
"scripts/rectification/candidate_contrast.py",
|
||||
"scripts/rectification/candidate_window.py",
|
||||
"scripts/rectification/case_holdout.py",
|
||||
"scripts/rectification/contracts.py",
|
||||
"scripts/rectification/dasha_transition_proximity.py",
|
||||
"scripts/rectification/decision_policy.py",
|
||||
"scripts/rectification/event_probes.py",
|
||||
"scripts/rectification/refinement_packet.py",
|
||||
"scripts/rectification/scoring_service.py",
|
||||
"scripts/shadbala.py",
|
||||
"scripts/varga.py"
|
||||
],
|
||||
"production_scoring_sha256": "788745f7b7aba1d551a73a67a56daff3e730c1d408cd77dde155e410ad9d00bb",
|
||||
"research_files": [
|
||||
"scripts/research/reported_offset_sweep.py",
|
||||
"scripts/research/cluster_width_lib.py",
|
||||
"scripts/research/probe_supply_after_six.py",
|
||||
"scripts/research/sealed_holdout_rerun.py",
|
||||
"scripts/minute_rectification_blind_eval.py",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py",
|
||||
"scripts/minute_rectification_holdout_validator.py"
|
||||
],
|
||||
"research_implementation_sha256": "fa74b52f52ca7beeb1c6c6647b11ef075c16bcb6fadb656196770d91004cd0ad",
|
||||
"file_sha256": {
|
||||
"scripts/active_rectification_event_engine.py": "cdc0e68edc770a2a1810fbdb68cbfd46dcd50b267c739c496fcc078c5e26b5b4",
|
||||
"scripts/active_rectification_events.py": "03e333ccf1103caf685dfe50fe890ab1793e945037085f50ce834a4a3b232222",
|
||||
"scripts/ashtakavarga.py": "9bfc0b8a06af6122fa6c3881706e64f28b9ba58b53d98ff55957d4741d820f3f",
|
||||
"scripts/dasha_analyzer.py": "5e53b1b4d4c7414c08dd0e7716f120a63c70ec3428ec93547f64d55c580da0e1",
|
||||
"scripts/divisional_charts_extended.py": "73bd50a83ac444830940184d0988cea621855f91db76a3f1a232014b992eacea",
|
||||
"scripts/domain_calculation_service.py": "9ee955874eea806c7b56f4246d90009c02ee8318b8f3dfe1d7132b1c0b4262e1",
|
||||
"scripts/functional_benefics.py": "cbaac3b8c09b97f8724b5300e9a402cbf77089af6c7db8788550d40fd35ac57b",
|
||||
"scripts/jaimini.py": "6b88658da5404da9b136686d92a04be462d61a39da6e8de4255021e2ed2d1173",
|
||||
"scripts/minute_rectification_blind_eval.py": "07aa30d8bad3278669495d5fea8be937aaf6367c8af980ff4f2fe9aa84ccc6ff",
|
||||
"scripts/minute_rectification_fact_blind_eval_v4.py": "bdf460e3467208e8b87345c5beb2128f3e22de7eeffd68f72b281b3ad9affc92",
|
||||
"scripts/minute_rectification_fact_ranker_v4.py": "f1a0d8d2482cd754d2e7f253a9606b0373519435a2bf58cfc3753e2b9ae0fb76",
|
||||
"scripts/minute_rectification_feature_facts_v4.py": "3d899a2cdd4825b8e32062443d487edcd2173a4ea55a36eb9f3abe587c0faf0f",
|
||||
"scripts/minute_rectification_holdout_validator.py": "b60b1c752e58672beaee8b36eb3b2348169726cda070ec969db0f13e7ed715af",
|
||||
"scripts/narayana_dasha.py": "7ff2c3238cd113b11b815e14b41967bd8e486ff62e36650e55613b9c79d1bfe3",
|
||||
"scripts/rectification/api_service.py": "e316ced0f3796d0378a0fe1aad950ee25922ae8afd53add578ed59ca8b2f0f79",
|
||||
"scripts/rectification/candidate_contrast.py": "eee7da71c0574a08876404b78ca111153fa95fb83ace82b9fdca141d1992e273",
|
||||
"scripts/rectification/candidate_window.py": "2fbc5058b12049b15fca375cdc125b8283e19f9f3e4bedcc291e344501891bef",
|
||||
"scripts/rectification/case_holdout.py": "fe0e699b617d9e216acdfeff87af4221c1d6f4c101bf33e1dbf14e2bcd75a8b5",
|
||||
"scripts/rectification/contracts.py": "c6dc6bd230e38f9f2126c224aae9ddbd6415304c15340f8c7cd3f06f6ef3160f",
|
||||
"scripts/rectification/dasha_transition_proximity.py": "0afba494aa12899621173c3cc941c6c1d0be9cec0bdf4c4a1c9bcd004ab22de8",
|
||||
"scripts/rectification/decision_policy.py": "80e8de4680d19a052213bb821d2a9c94143a2962235aeb27f6ad81374d2e60d5",
|
||||
"scripts/rectification/event_probes.py": "9bbadc246e6b8e94bb047522c3e5645613f508b3473ef40b38a207c77fdad58c",
|
||||
"scripts/rectification/refinement_packet.py": "dbeea5aa780889785ce850f3881e8b7f67bb44594e9bc382c65b2e730884a2f4",
|
||||
"scripts/rectification/scoring_service.py": "4f13c6a78d2dda55454ac20e4091fce280e3626ecfe8a9d723217ef3ebc05d02",
|
||||
"scripts/research/cluster_width_lib.py": "1d8f2ffa7795d62069deebb2de8e16749317037d4ed3f24a2c0092676e5cfcc6",
|
||||
"scripts/research/probe_supply_after_six.py": "098a5b4398d6f8d996917d809c2fc922ad64031d3b70660f8ef7c876aba92438",
|
||||
"scripts/research/reported_offset_sweep.py": "f63c1c58d334e083577736397b4acc00757550fa3b863b02784c9d6f0f018c80",
|
||||
"scripts/research/sealed_holdout_rerun.py": "1178ebfb9dd61d4aefe9961d83f19e7a943a4ca3de9fa2efffff6f8ba8c09161",
|
||||
"scripts/shadbala.py": "e949ff1cc925ccbc9a25b68981091d1d621b80a5b3839a3b3ade655d082424d6",
|
||||
"scripts/varga.py": "4331de5a25ea08729af91aae863943c4223183937f419d52dc63fd6fe7f27be6"
|
||||
},
|
||||
"hash_scope": "explicit_identity_file_sets_not_a_transitive_dependency_lock"
|
||||
},
|
||||
"scorer_frozen_before_rerun": true,
|
||||
"source_audit_status": "corrected_known_date_errors",
|
||||
"trial_count": 20,
|
||||
"official_valid_independent_blind": false,
|
||||
"is_blind_evaluation": false,
|
||||
"truth_hidden_from_ranker": true,
|
||||
"results_previously_seen": true,
|
||||
"must_not_claim_as_release_metrics": true,
|
||||
"must_not_use_for_tuning": true,
|
||||
"verified_minute_claim_allowed": false,
|
||||
"metric_gates_passed": false,
|
||||
"events_per_case": 3,
|
||||
"boundary": "Previously exposed v3 shadow fixed-protocol rerun after the 2026-10-03 astrologer rulings batch 1 re-freeze. Superseded by the 2026-10-07 upstream sync 6 re-freeze (ERR-110: scripts/varga.py, scripts/divisional_charts_extended.py, scripts/narayana_dasha.py and scripts/rectification/scoring_service.py bytes changed by the PVR 6.2 D5/D6/D8/D11 maps and the scoring-11 identity, BUG-1260/1264). Shadow trial fields versus the 2026-09-20 historical report are unchanged (changed_trial_count 0). Report and freeze preserved byte-for-byte.",
|
||||
"report_sha256": "b39b53c1f2aa0ad6ac363b4c359116c30bc89b446cb670e6172c8cee5ccc5efd",
|
||||
"freeze_record_sha256": "c1c11e7abc03b9174aeb1e0b280f550808f887818f578e5d10ad667e0da67e24",
|
||||
"replay_started_at_utc": "2026-10-03T06:53:04.851491+00:00",
|
||||
"replay_finished_at_utc": "2026-10-03T06:53:07.509845+00:00",
|
||||
"previous_fixed_protocol_rerun": {
|
||||
"report_path": "docs/research/sealed_holdout_rerun_upstream_sync5_2026_10_02.json",
|
||||
"freeze_record_path": "docs/research/sealed_holdout_rerun_upstream_sync5_2026_10_02.freeze.json",
|
||||
"superseded_reason": "Upstream sync round 6 (ERR-110). Prior sync5 report and freeze preserved byte-for-byte."
|
||||
}
|
||||
},
|
||||
"current_tree_unfrozen_diagnostic": {
|
||||
"is_blind_evaluation": false,
|
||||
"results_already_seen": true,
|
||||
@@ -330,6 +330,28 @@
|
||||
"verified_minute_claim_allowed": false
|
||||
},
|
||||
"current_tree_reported_offset_replay": {
|
||||
"report_path": "docs/research/reported_offset_upstream_sync9b_2026_10_28.json",
|
||||
"report_sha256": "880bebc2e217100994a1442e47ead3f9d33e48aa3ac20f69d993f38def3ef25c",
|
||||
"freeze_record_path": "docs/research/reported_offset_upstream_sync9b_2026_10_28.freeze.json",
|
||||
"freeze_record_sha256": "385817bb27f04afeba230af5e547dd10dc8cf6db4b25c18bebe4f4e674cab972",
|
||||
"scope": "reported_offset_sensitivity_not_product_accuracy",
|
||||
"trial_count": 900,
|
||||
"official_valid_independent_blind": false,
|
||||
"official_blind_trial_count": 0,
|
||||
"must_not_use_for_tuning": true,
|
||||
"must_not_claim_as_release_metrics": true,
|
||||
"replay_started_at_utc": "2026-10-28T08:19:10.206540+00:00",
|
||||
"replay_finished_at_utc": "2026-10-28T08:23:34.348635+00:00",
|
||||
"boundary": "Previously exposed reported-offset sensitivity after upstream sync9b (ERR-110, BUG-1494 to BUG-1495). Summary and trials match the 2026-10-18 upstream sync8 report. Versus the 2026-09-20 historical report, changed_trial_count stays 581 of 900. Not a release metric. No tuning. Prior sync8 report and freeze preserved byte-for-byte.",
|
||||
"previous_reported_offset_replay": {
|
||||
"report_path": "docs/research/reported_offset_upstream_sync8_2026_10_18.json",
|
||||
"report_sha256": "a51aad2e743dccba7726d1a0a5e44c5e431ff429fe1725c9be2f7fa5e9282da6",
|
||||
"freeze_record_path": "docs/research/reported_offset_upstream_sync8_2026_10_18.freeze.json",
|
||||
"freeze_record_sha256": "117ab0bfa4a283e9d52073808f71dd8317f613c96b27ec271d887ef40087f4f5",
|
||||
"superseded_reason": "Upstream sync9b (BUG-1494 to BUG-1495) changed scripts/varga.py, which is part of the extended identity. Output is unchanged, so ERR-110 stored a new record. Prior sync8 report and freeze preserved byte-for-byte."
|
||||
}
|
||||
},
|
||||
"previous_reported_offset_replay": {
|
||||
"report_path": "docs/research/reported_offset_upstream_sync8_2026_10_18.json",
|
||||
"report_sha256": "a51aad2e743dccba7726d1a0a5e44c5e431ff429fe1725c9be2f7fa5e9282da6",
|
||||
"freeze_record_path": "docs/research/reported_offset_upstream_sync8_2026_10_18.freeze.json",
|
||||
@@ -350,12 +372,5 @@
|
||||
"freeze_record_sha256": "1560f24ffea19116c904272907ff9cce24904960406676f3aada3c8c174cf98a",
|
||||
"superseded_reason": "Upstream sync8 (BUG-1380 to BUG-1390) changed frozen identity files. Output is unchanged, so ERR-110 stored a new record. Versus the 2026-09-20 historical report, changed_trial_count stays 581 of 900. Prior scoring_perf report and freeze preserved byte-for-byte."
|
||||
}
|
||||
},
|
||||
"previous_reported_offset_replay": {
|
||||
"report_path": "docs/research/reported_offset_astrologer_rulings_batch1_2026_10_03.json",
|
||||
"report_sha256": "480eb771c2c7e5a300589561dc66be950a711ffa205a8fa370db6a11f1e04270",
|
||||
"freeze_record_path": "docs/research/reported_offset_astrologer_rulings_batch1_2026_10_03.freeze.json",
|
||||
"freeze_record_sha256": "6be6a997f610c341aecc1f782fa27a5b86b66d43d00fcfa10750c81189c34748",
|
||||
"superseded_reason": "Upstream sync 6 (ERR-110: scripts/varga.py, scripts/divisional_charts_extended.py, scripts/narayana_dasha.py and scripts/rectification/scoring_service.py). 5 of 900 trials differ from the batch1 replay (delivery_width_minutes on 4, top_1_minute_error on 1). Versus the 2026-09-20 historical report, changed_trial_count is 235 (batch1 was 230). Prior report and freeze preserved byte-for-byte."
|
||||
}
|
||||
}
|
||||
|
||||
@@ -30,11 +30,11 @@ from scripts.research.sealed_holdout_rerun import (
|
||||
OFFSETS = (-30, -20, -15, -10, -8, -5, -3, 0, 3, 5, 8, 10, 15, 20, 30)
|
||||
RADII = (15, 30, 60)
|
||||
MINUTE_STEP = 1
|
||||
# 原值: docs/research/reported_offset_scoring_perf_2026_10_13.{freeze.json,json}
|
||||
# 新值: docs/research/reported_offset_upstream_sync8_2026_10_18.{freeze.json,json}
|
||||
# 原因: sync8(BUG-1380~1389)改了 ashtakavarga / dasha_analyzer / narayana_dasha,输出不变,ERR-110 另存新记录
|
||||
FREEZE = ROOT / "docs/research/reported_offset_upstream_sync8_2026_10_18.freeze.json"
|
||||
REPORT = ROOT / "docs/research/reported_offset_upstream_sync8_2026_10_18.json"
|
||||
# 原值: docs/research/reported_offset_upstream_sync8_2026_10_18.{freeze.json,json}
|
||||
# 新值: docs/research/reported_offset_upstream_sync9b_2026_10_28.{freeze.json,json}
|
||||
# 原因: sync9b(BUG-1494~1495)改了 scripts/varga.py,它在扩展身份里;报时窗口输出不变,ERR-110 另存新记录
|
||||
FREEZE = ROOT / "docs/research/reported_offset_upstream_sync9b_2026_10_28.freeze.json"
|
||||
REPORT = ROOT / "docs/research/reported_offset_upstream_sync9b_2026_10_28.json"
|
||||
LEGACY_REPORT = ROOT / "docs/research/reported_offset_2026_09_20.json"
|
||||
|
||||
|
||||
|
||||
@@ -27,11 +27,11 @@ from scripts.minute_rectification_feature_facts_v4 import build_feature_fact_row
|
||||
from scripts.minute_rectification_holdout_validator import validate
|
||||
|
||||
DATASET = ROOT / "references/real_case_calibration/minute_rectification_holdout_v3.json"
|
||||
# 原值: docs/research/sealed_holdout_rerun_scoring_perf_2026_10_13.{freeze.json,json}
|
||||
# 新值: docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.{freeze.json,json}
|
||||
# 原因: sync8(BUG-1380~1389)改了 ashtakavarga / dasha_analyzer / narayana_dasha,输出不变,ERR-110 另存新记录
|
||||
FREEZE = ROOT / "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.freeze.json"
|
||||
REPORT = ROOT / "docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.json"
|
||||
# 原值: docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18.{freeze.json,json}
|
||||
# 新值: docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.{freeze.json,json}
|
||||
# 原因: sync9b(BUG-1494~1495)改了 scripts/varga.py,它在扩展身份里;切盘输出不变,ERR-110 另存新记录
|
||||
FREEZE = ROOT / "docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.freeze.json"
|
||||
REPORT = ROOT / "docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28.json"
|
||||
LEGACY_REPORT = ROOT / "docs/research/sealed_holdout_rerun_2026_09_20.json"
|
||||
ARCHIVE = ROOT / "docs/research/history/rectification_pre_cross_midnight_2026_09_20"
|
||||
PRODUCTION_FILES = [
|
||||
|
||||
+12
-8
@@ -246,11 +246,12 @@ def calc_64th_navamsa(moon_lon: float) -> Dict:
|
||||
def calc_22nd_drekkana(lagna_lon: float) -> Dict:
|
||||
"""Compute the 22nd Drekkana from the Lagna's Drekkana position.
|
||||
|
||||
Traditional counting is inclusive, so the 22nd point is +21 signs from the
|
||||
Lagna Drekkana anchor.
|
||||
Crux of Vedic Astrology, printed p.329 (corpus page 340), identifies
|
||||
this as the eighth house in D3. Counting 21 ten-degree divisions is
|
||||
not the same as moving 21 signs in the D3 chart.
|
||||
"""
|
||||
base = calc_varga(lagna_lon, 3)
|
||||
sign_idx = (base['sign_idx'] + 21) % 12
|
||||
sign_idx = (base['sign_idx'] + 7) % 12
|
||||
return {
|
||||
'base_drekkana_sign_idx': base['sign_idx'],
|
||||
'base_drekkana_sign': base['sign'],
|
||||
@@ -279,16 +280,19 @@ def calc_bhrigu_bindu(moon_lon: float, rahu_lon: float) -> Dict:
|
||||
}
|
||||
|
||||
|
||||
SARPA_DREKKANA_SIGNS = {'Cancer': 2, 'Scorpio': 1, 'Pisces': 3}
|
||||
# Raman, Hindu Predictive Astrology, Drekkanas chapter, corpus pp.279–283:
|
||||
# five serpent divisions, including both Cancer-3 and Scorpio-2.
|
||||
SARPA_DREKKANA_SIGNS = {'Cancer': (2, 3), 'Scorpio': (1, 2), 'Pisces': (3,)}
|
||||
|
||||
|
||||
def calc_sarpa_drekkana(lon: float) -> Dict:
|
||||
"""Classify Sarpa Drekkana using the classical water-sign sensitive drekkanas."""
|
||||
lon = lon % 360
|
||||
base = calc_varga(lon, 3)
|
||||
sign = _sn(_si(lon))
|
||||
degree_in_sign = round((lon % 30), 4)
|
||||
drekkana_number = int(degree_in_sign / 10) + 1
|
||||
expected = SARPA_DREKKANA_SIGNS.get(sign)
|
||||
drekkana_number = int((lon % 30) / 10) + 1
|
||||
expected = SARPA_DREKKANA_SIGNS.get(sign, ())
|
||||
return {
|
||||
'longitude': round(lon % 360, 4),
|
||||
'sign': sign,
|
||||
@@ -297,8 +301,8 @@ def calc_sarpa_drekkana(lon: float) -> Dict:
|
||||
'drekkana_number': drekkana_number,
|
||||
'd3_sign': base['sign'],
|
||||
'd3_sign_idx': base['sign_idx'],
|
||||
'is_sarpa_drekkana': bool(expected == drekkana_number),
|
||||
'definition': 'Cancer-2, Scorpio-1, Pisces-3',
|
||||
'is_sarpa_drekkana': drekkana_number in expected,
|
||||
'definition': 'Cancer-2, Cancer-3, Scorpio-1, Scorpio-2, Pisces-3',
|
||||
}
|
||||
|
||||
def dignity(planet, sign_idx):
|
||||
|
||||
@@ -701,7 +701,7 @@ def test_full_reading_exposes_sensitive_point_modules() -> None:
|
||||
assert sensitive["bhrigu_bindu"]["sign"]
|
||||
assert isinstance(sensitive["sarpa_drekkana"], dict)
|
||||
for payload in sensitive["sarpa_drekkana"].values():
|
||||
assert payload["definition"] == "Cancer-2, Scorpio-1, Pisces-3"
|
||||
assert payload["definition"] == "Cancer-2, Cancer-3, Scorpio-1, Scorpio-2, Pisces-3"
|
||||
assert payload["is_sarpa_drekkana"] is True
|
||||
|
||||
|
||||
|
||||
@@ -51,8 +51,11 @@ IDENTITY_FORBIDDEN_PREFIXES = (
|
||||
# 原值: 排除到 scoring_perf_2026_10_13
|
||||
# 新值: 再排除 upstream_sync8_2026_10_18 两份冻结路径
|
||||
# 原因: sync8 改了冻结身份文件,输出不变,ERR-110 另存新记录
|
||||
"docs/research/sealed_holdout_rerun_upstream_sync8_2026_10_18",
|
||||
"docs/research/reported_offset_upstream_sync8_2026_10_18",
|
||||
# 原值: 排除到 upstream_sync8_2026_10_18
|
||||
# 新值: 再排除 upstream_sync9b_2026_10_28 两份冻结路径
|
||||
# 原因: sync9b 改了扩展身份里的 scripts/varga.py,回放输出不变,ERR-110 另存新记录
|
||||
"docs/research/sealed_holdout_rerun_upstream_sync9b_2026_10_28",
|
||||
"docs/research/reported_offset_upstream_sync9b_2026_10_28",
|
||||
"docs/research/history/",
|
||||
"artifacts/",
|
||||
)
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
"""Classification must use raw longitude, never rounded display degrees."""
|
||||
import pytest
|
||||
|
||||
from scripts.varga import calc_sarpa_drekkana
|
||||
|
||||
|
||||
@pytest.mark.parametrize('longitude,part,is_sarpa', [
|
||||
(99.99999, 1, False), (100.0, 2, True),
|
||||
(219.99999, 1, True), (220.0, 2, True),
|
||||
(359.99999, 3, True), (360.0, 1, False),
|
||||
])
|
||||
def test_sarpa_partition_uses_unrounded_longitude(longitude, part, is_sarpa):
|
||||
row = calc_sarpa_drekkana(longitude)
|
||||
assert row['drekkana_number'] == part
|
||||
assert row['is_sarpa_drekkana'] is is_sarpa
|
||||
assert 1 <= row['drekkana_number'] <= 3
|
||||
@@ -0,0 +1,225 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Regression tests for BPHS divisional chart mappings."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import pytest
|
||||
|
||||
pytest.importorskip(
|
||||
"hypothesis",
|
||||
reason="hypothesis is not installed; see requirements-dev.txt. "
|
||||
"The guard keeps this file collectable: without it the whole file "
|
||||
"fails to collect and its tests vanish from the run instead of failing.",
|
||||
)
|
||||
|
||||
|
||||
from hypothesis import given
|
||||
from hypothesis import strategies as st
|
||||
from varga import (
|
||||
SIGNS,
|
||||
calc_22nd_drekkana,
|
||||
calc_64th_navamsa,
|
||||
calc_bhrigu_bindu,
|
||||
calc_all_vargas,
|
||||
calc_sarpa_drekkana,
|
||||
calc_varga,
|
||||
varga_map,
|
||||
)
|
||||
|
||||
|
||||
def navamsa_ref(lon: float) -> int:
|
||||
sign_index = int((lon % 360) / 30) % 12
|
||||
degree_in_sign = (lon % 360) - sign_index * 30
|
||||
part_index = int(degree_in_sign / (30 / 9))
|
||||
if sign_index % 3 == 0:
|
||||
start = sign_index
|
||||
elif sign_index % 3 == 1:
|
||||
start = (sign_index + 8) % 12
|
||||
else:
|
||||
start = (sign_index + 4) % 12
|
||||
return (start + part_index) % 12
|
||||
|
||||
|
||||
def dasamsa_ref(lon: float) -> int:
|
||||
sign_index = int((lon % 360) / 30) % 12
|
||||
degree_in_sign = (lon % 360) - sign_index * 30
|
||||
part_index = int(degree_in_sign / 3)
|
||||
start = sign_index if sign_index % 2 == 0 else (sign_index + 8) % 12
|
||||
return (start + part_index) % 12
|
||||
|
||||
|
||||
def drekkana_ref(lon: float) -> int:
|
||||
sign_index = int((lon % 360) / 30) % 12
|
||||
degree_in_sign = (lon % 360) - sign_index * 30
|
||||
part_index = int(degree_in_sign / 10)
|
||||
return (sign_index + part_index * 4) % 12
|
||||
|
||||
|
||||
def chaturthamsa_ref(lon: float) -> int:
|
||||
sign_index = int((lon % 360) / 30) % 12
|
||||
degree_in_sign = (lon % 360) - sign_index * 30
|
||||
part_index = int(degree_in_sign / (30 / 4))
|
||||
return (sign_index + part_index * 3) % 12
|
||||
|
||||
|
||||
@given(st.floats(min_value=0, max_value=359.999999, allow_nan=False, allow_infinity=False))
|
||||
def test_navamsa_matches_bphs_reference(lon: float) -> None:
|
||||
result = calc_varga(lon, 9)
|
||||
assert result["sign_idx"] == navamsa_ref(lon)
|
||||
assert result["sign"] == SIGNS[navamsa_ref(lon)]
|
||||
assert 0 <= result["degree_in_sign"] < 30
|
||||
|
||||
|
||||
@given(st.floats(min_value=0, max_value=359.999999, allow_nan=False, allow_infinity=False))
|
||||
def test_dasamsa_matches_bphs_reference(lon: float) -> None:
|
||||
result = calc_varga(lon, 10)
|
||||
assert result["sign_idx"] == dasamsa_ref(lon)
|
||||
assert result["sign"] == SIGNS[dasamsa_ref(lon)]
|
||||
assert 0 <= result["degree_in_sign"] < 30
|
||||
|
||||
|
||||
@given(st.floats(min_value=0, max_value=359.999999, allow_nan=False, allow_infinity=False))
|
||||
def test_drekkana_uses_same_plus_four_plus_eight(lon: float) -> None:
|
||||
result = calc_varga(lon, 3)
|
||||
assert result["sign_idx"] == drekkana_ref(lon)
|
||||
|
||||
|
||||
@given(st.floats(min_value=0, max_value=359.999999, allow_nan=False, allow_infinity=False))
|
||||
def test_chaturthamsa_matches_pyjhora_parashara_reference(lon: float) -> None:
|
||||
result = calc_varga(lon, 4)
|
||||
assert result["sign_idx"] == chaturthamsa_ref(lon)
|
||||
assert result["sign"] == SIGNS[chaturthamsa_ref(lon)]
|
||||
assert 0 <= result["degree_in_sign"] < 30
|
||||
|
||||
|
||||
def test_chaturthamsa_reference_boundary_examples() -> None:
|
||||
assert [varga_map(0, part, 4) for part in range(4)] == [0, 3, 6, 9]
|
||||
assert [varga_map(8, part, 4) for part in range(4)] == [8, 11, 2, 5]
|
||||
assert [varga_map(11, part, 4) for part in range(4)] == [11, 2, 5, 8]
|
||||
|
||||
|
||||
def test_varga_map_boundary_examples() -> None:
|
||||
assert varga_map(0, 0, 9) == 0 # Aries Navamsa starts Aries
|
||||
assert varga_map(1, 0, 9) == 9 # Taurus Navamsa starts Capricorn (9th from sign)
|
||||
assert varga_map(2, 0, 9) == 6 # Gemini Navamsa starts Libra (5th from sign)
|
||||
assert varga_map(1, 0, 10) == 9 # Taurus Dasamsa starts Capricorn
|
||||
assert varga_map(0, 2, 3) == 8 # Aries third Drekkana = Sagittarius
|
||||
|
||||
|
||||
def test_rudramsa_d11_is_supported_by_native_varga_map() -> None:
|
||||
assert varga_map(0, 0, 11) == 0
|
||||
assert varga_map(0, 10, 11) == 10
|
||||
# PVR 6.2.11: anti-zodiacal seed from Aries, zodiacal parts.
|
||||
assert varga_map(1, 0, 11) == 11
|
||||
assert varga_map(1, 10, 11) == 9
|
||||
result = calc_varga(35.0, 11)
|
||||
assert result["sign"] == "Aries"
|
||||
assert 0 <= result["degree_in_sign"] < 30
|
||||
|
||||
|
||||
def test_native_varga_map_supports_declared_high_value_vargas() -> None:
|
||||
for div in (2, 4, 5, 6, 7, 8, 9, 10, 11, 12, 24, 60, 81, 108, 144):
|
||||
result = calc_varga(35.0, div)
|
||||
assert result["sign"] in SIGNS
|
||||
assert 0 <= result["degree_in_sign"] < 30
|
||||
|
||||
|
||||
def test_default_varga_batch_includes_declared_vargas() -> None:
|
||||
charts = calc_all_vargas({"Moon": 35.0}, 10.0)
|
||||
for key in ("D5_Panchamsa", "D6_Shashthamsa", "D8_Ashtamsa", "D11_Rudramsa", "D81_Navamsa-Navamsa", "D108_Dwadasamsa-Navamsa", "D144_Dwadasamsa-Dwadasamsa"):
|
||||
assert key in charts
|
||||
assert charts["D11_Rudramsa"]["Moon"]["sign"] == "Aries"
|
||||
|
||||
|
||||
def test_navamsa_matches_user_jhora_pdf_reference_chart() -> None:
|
||||
"""Regression from private_chart_reference.pdf: JHora-style D9 table for public sample birth datetime San Francisco."""
|
||||
expected = {
|
||||
132.355025: "Cancer", # Ascendant 12 Leo 21'18.09"
|
||||
3.5226611111111112: "Taurus",
|
||||
311.78995555555554: "Capricorn",
|
||||
91.33091388888889: "Cancer",
|
||||
338.5488: "Virgo",
|
||||
163.83150833333335: "Taurus",
|
||||
340.5554638888889: "Libra",
|
||||
304.3033805555556: "Scorpio",
|
||||
231.04509444444443: "Capricorn",
|
||||
51.045094444444445: "Cancer",
|
||||
}
|
||||
for longitude, expected_sign in expected.items():
|
||||
assert calc_varga(longitude, 9)["sign"] == expected_sign
|
||||
|
||||
|
||||
def test_64th_navamsa_counts_forward_from_moon_navamsa() -> None:
|
||||
moon_lon = 42.3
|
||||
result = calc_64th_navamsa(moon_lon)
|
||||
expected_sign_idx = (navamsa_ref(moon_lon) + 63) % 12
|
||||
assert result["sign_idx"] == expected_sign_idx
|
||||
assert result["sign"] == SIGNS[expected_sign_idx]
|
||||
assert result["offset_from_moon_navamsa"] == 64
|
||||
|
||||
|
||||
def test_22nd_drekkana_counts_forward_from_lagna_drekkana() -> None:
|
||||
asc_lon = 25.5
|
||||
result = calc_22nd_drekkana(asc_lon)
|
||||
# Sagittarius D3 rising: its eighth house is Cancer (Crux p.329).
|
||||
expected_sign_idx = 3
|
||||
assert result["sign_idx"] == expected_sign_idx
|
||||
assert result["sign"] == SIGNS[expected_sign_idx]
|
||||
assert result["offset_from_lagna_drekkana"] == 22
|
||||
|
||||
|
||||
def test_22nd_drekkana_independent_zodiac_partition_count() -> None:
|
||||
# Enumerate all 36 zodiacal ten-degree divisions, then count 22 inclusively.
|
||||
# This oracle does not add an offset to the calculated D3 sign.
|
||||
for division in range(36):
|
||||
target = (division + 21) % 36
|
||||
target_rasi, target_part = divmod(target, 3)
|
||||
expected = (target_rasi + 4 * target_part) % 12
|
||||
for within in (0.0, 0.001, 5.0, 9.999):
|
||||
result = calc_22nd_drekkana(division * 10 + within)
|
||||
assert result['sign_idx'] == expected
|
||||
|
||||
|
||||
def test_bhrigu_bindu_uses_rahu_to_moon_arc_midpoint() -> None:
|
||||
result = calc_bhrigu_bindu(270.5, 160.2333333333)
|
||||
assert result["longitude"] == 215.3667
|
||||
assert result["sign"] == "Scorpio"
|
||||
assert result["degree_in_sign"] == 5.3667
|
||||
|
||||
|
||||
def test_bhrigu_bindu_handles_wraparound_across_zero_aries() -> None:
|
||||
result = calc_bhrigu_bindu(10.0, 350.0)
|
||||
assert result["longitude"] == 0.0
|
||||
assert result["sign"] == "Aries"
|
||||
assert result["degree_in_sign"] == 0.0
|
||||
|
||||
|
||||
def test_sarpa_drekkana_detects_classical_sensitive_ranges() -> None:
|
||||
cancer_second = calc_sarpa_drekkana(105.0)
|
||||
scorpio_first = calc_sarpa_drekkana(215.0)
|
||||
pisces_third = calc_sarpa_drekkana(355.0)
|
||||
safe_aries = calc_sarpa_drekkana(15.0)
|
||||
|
||||
assert cancer_second["is_sarpa_drekkana"] is True
|
||||
assert cancer_second["sign"] == "Cancer"
|
||||
assert cancer_second["drekkana_number"] == 2
|
||||
|
||||
assert scorpio_first["is_sarpa_drekkana"] is True
|
||||
assert scorpio_first["sign"] == "Scorpio"
|
||||
assert scorpio_first["drekkana_number"] == 1
|
||||
|
||||
assert pisces_third["is_sarpa_drekkana"] is True
|
||||
assert pisces_third["sign"] == "Pisces"
|
||||
assert pisces_third["drekkana_number"] == 3
|
||||
|
||||
assert safe_aries["is_sarpa_drekkana"] is False
|
||||
|
||||
|
||||
def test_sarpa_contains_all_five_book_ranges_and_no_others() -> None:
|
||||
# Zodiac degree intervals transcribed from Raman, not the production map.
|
||||
intervals = ((100, 120), (210, 230), (350, 360))
|
||||
for segment in range(36):
|
||||
for offset in (0.0, 0.001, 5.0, 9.999):
|
||||
longitude = segment * 10 + offset
|
||||
expected = any(start <= longitude < end for start, end in intervals)
|
||||
assert calc_sarpa_drekkana(longitude)['is_sarpa_drekkana'] == expected
|
||||
@@ -175,7 +175,8 @@ def test_64th_navamsa_counts_forward_from_moon_navamsa() -> None:
|
||||
def test_22nd_drekkana_counts_forward_from_lagna_drekkana() -> None:
|
||||
asc_lon = 25.5
|
||||
result = calc_22nd_drekkana(asc_lon)
|
||||
expected_sign_idx = (drekkana_ref(asc_lon) + 21) % 12
|
||||
# Sagittarius D3 rising: its eighth house is Cancer (Crux p.329).
|
||||
expected_sign_idx = 3
|
||||
assert result["sign_idx"] == expected_sign_idx
|
||||
assert result["sign"] == SIGNS[expected_sign_idx]
|
||||
assert result["offset_from_lagna_drekkana"] == 22
|
||||
|
||||
Reference in New Issue
Block a user