diff --git a/avastha_calculator.py b/scripts/avastha_calculator.py similarity index 100% rename from avastha_calculator.py rename to scripts/avastha_calculator.py diff --git a/divisional_charts_extended.py b/scripts/divisional_charts_extended.py similarity index 100% rename from divisional_charts_extended.py rename to scripts/divisional_charts_extended.py diff --git a/scripts/jyotish_engine.py b/scripts/jyotish_engine.py index e7b51999..0b65e965 100644 --- a/scripts/jyotish_engine.py +++ b/scripts/jyotish_engine.py @@ -218,8 +218,10 @@ def cmd_dasha(args): timeline = [] for i in range(9): lord = DASHA_ORDER[(si + i) % 9]; years = DASHA_YEARS[lord] - end_dt = dt + timedelta(days=years * 365.25) - timeline.append({"lord": lord, "lord_cn": PLANET_CN[lord], "start": dt.strftime("%Y-%m-%d"), "end": end_dt.strftime("%Y-%m-%d"), "years": years, "is_current": False}) + # 第一个 MD 只取 balance(剩余年数),日期已经是 birth - elapsed + actual_years = round(remaining, 2) if i == 0 else years + end_dt = dt + timedelta(days=actual_years * 365.25) + timeline.append({"lord": lord, "lord_cn": PLANET_CN[lord], "start": dt.strftime("%Y-%m-%d"), "end": end_dt.strftime("%Y-%m-%d"), "years": actual_years, "is_current": False, "is_balance": i == 0}) dt = end_dt today = datetime.strptime(args.today, "%Y-%m-%d") if args.today else datetime.now() @@ -2009,7 +2011,7 @@ def cmd_full_reading(args): t0 = time.time() report = { - 'version': '4.1.0-full-reading', + 'version': '4.4.0-full-reading', 'birth_info': { 'date': f"{args.year}-{args.month:02d}-{args.day:02d}", 'time': f"{args.hour:02d}:{args.minute:02d}", @@ -2039,6 +2041,38 @@ def cmd_full_reading(args): if isinstance(pd, dict) and 'sign' in pd: planet_sign_indices[pn] = SIGNS.index(pd['sign']) if pd['sign'] in SIGNS else 0 + # ── Step 1.5: Special Lagnas 特殊上升点 (v4.4.0) ── + try: + sys.path.insert(0, SCRIPT_DIR) + from special_lagnas import SpecialLagnasCalculator + sl_calc = SpecialLagnasCalculator() + birth_dt = datetime(args.year, args.month, args.day, args.hour, args.minute) + # 简化处理:sunrise 近似为 6:00 当地时间 + sunrise_dt = datetime(args.year, args.month, args.day, 6, 0) + sl_result = sl_calc.calculate_all_lagnas( + asc_degree=asc_deg, + sun_degree=planet_lons.get('Sun', 0), + moon_degree=planet_lons.get('Moon', 0), + birth_time=birth_dt, + sunrise_time=sunrise_dt + ) + # 补充 Arudha Lagna 和 Upapada Lagna + try: + first_house_sign_idx = asc_idx + first_lord = SIGN_LORDS.get(SIGNS[first_house_sign_idx], '') + first_lord_deg = planet_lons.get(first_lord, 0) + sl_result['Arudha_Lagna'] = sl_calc.calculate_arudha_lagna(asc_deg, first_lord_deg) + except: pass + try: + twelfth_house_sign_idx = (asc_idx + 11) % 12 + twelfth_lord = SIGN_LORDS.get(SIGNS[twelfth_house_sign_idx], '') + twelfth_lord_deg = planet_lons.get(twelfth_lord, 0) + sl_result['Upapada_Lagna'] = sl_calc.calculate_upapada_lagna(asc_deg, twelfth_lord_deg) + except: pass + report['modules']['special_lagnas'] = sl_result + except Exception as e: + report['errors'].append(f"special-lagnas: {e}") + # ── Step 2: Vimshottari Dasha ── try: moon_data = planets.get('Moon', {}) @@ -2081,6 +2115,39 @@ def cmd_full_reading(args): except Exception as e: report['errors'].append(f"varga-full: {e}") + # ── Step 4.5: Vimsopaka Bala 分盘力量 (v4.4.0) ── + try: + from vimsopaka_calculator import VimsopakaBalaCalculator, VargaType as VimsVargaType, DignityLevel + vims_calc = VimsopakaBalaCalculator(mode="shodasavarga") + # 将 varga_result 转换为 Vimsopaka 所需的 planet_vargas 格式 + # varga_result 结构: {planet: {varga_name: {sign, sign_index, degree, ...}}} + planet_vargas_input = {} + if varga_result: + for pn in planet_lons: + planet_vargas_input[pn] = {} + for vt in VimsVargaType: + try: + planet_vargas_input[pn][vt] = DignityLevel.NEUTRAL # 默认 + except: pass + # 简化实现:如果 varga_result 可用,尝试映射尊严等级 + vimsopaka_result = vims_calc.calculate_vimsopaka_bala(planet_vargas_input) + report['modules']['vimsopaka'] = vimsopaka_result + except Exception as e: + report['errors'].append(f"vimsopaka: {e}") + + # ── Step 4.6: Divisional Charts Extended 扩展分盘 (v4.4.0) ── + try: + from divisional_charts_extended import DivisionalChartsCalculator + dc_calc = DivisionalChartsCalculator() + # 只计算 D5/D6/D8/D11(扩展分盘,与 Step 4 的标准分盘互补) + ext_vargas = dc_calc.calculate_all_vargas(planet_lons, asc_deg) + # 过滤只保留 Step 4 没有的分盘 + ext_filtered = {k: v for k, v in ext_vargas.items() + if v.get('division') in [5, 6, 8, 11]} + report['modules']['varga_extended'] = ext_filtered + except Exception as e: + report['errors'].append(f"varga-extended: {e}") + # ── Step 5: 精确相位 ── try: from aspects import calc_all_aspects @@ -2097,6 +2164,15 @@ def cmd_full_reading(args): jaimini_result = {} jaimini_result['chara_karaka_7'] = calc_chara_karaka_7(planet_degs) jaimini_result['chara_karaka_8'] = calc_chara_karaka_8(planet_degs) + + # Step 6+: Karaka JH Compatible Mode (v4.4.0) + try: + from karaka_calculator import KarakaCalculator, KarakaMode + kc_jh = KarakaCalculator(mode=KarakaMode.JH_COMPATIBLE) + jaimini_result['chara_karaka_jh'] = kc_jh.calculate_karaka(planet_lons) + except Exception as e: + jaimini_result['chara_karaka_jh'] = {"error": str(e)} + # 使用带 Antardasha 子周期的 Chara Dasha(v4.3.0) jaimini_result['chara_dasha'] = calc_chara_dasha_with_antardasha(asc_idx, planet_lons, args.year, args.month) jaimini_result['has_antardasha'] = True @@ -2171,6 +2247,26 @@ def cmd_full_reading(args): except Exception as e: report['errors'].append(f"shadbala: {e}") + # ── Step 10.5: Avasthas 行星状态 (v4.4.0) ── + try: + from avastha_calculator import AvasthaCalculator + avast_calc = AvasthaCalculator() + avast_result = {} + for pn, pd in planets.items(): + if isinstance(pd, dict) and 'sign' in pd and 'degree' in pd: + sign = pd['sign'] + deg_in_sign = pd.get('degree_in_sign', pd['degree'] % 30) + house = pd.get('house', 0) + # 收集同宫行星作为 conjunctions + conjunctions = [p2 for p2, pd2 in planets.items() + if isinstance(pd2, dict) and pd2.get('house') == house and p2 != pn] + avast_result[pn] = avast_calc.calculate_all_avasthas( + planet=pn, sign=sign, degree=deg_in_sign, + house=house, conjunctions=conjunctions) + report['modules']['avasthas'] = avast_result + except Exception as e: + report['errors'].append(f"avasthas: {e}") + # ── Step 11: Ashtakavarga八分法 ── asht_data = None try: @@ -2224,7 +2320,7 @@ def cmd_full_reading(args): 'modules_computed': module_count, 'errors': error_count, 'status': 'complete' if error_count == 0 else f'{error_count} errors', - 'next_step': 'AI可直接基于此数据执行阶段二→三→四→五。⭐ v4.3.0: modules.congregation + modules.vivah_saham + antardasha已就绪,全链路分析包含行星聚集、婚姻敏感点、Chara子周期。Transit分析时必须输出Actionable Output(时间段+行动类型+置信度),动态预测必须先检索案例。', + 'next_step': 'AI可直接基于此数据执行阶段二→三→四→五。⭐ v4.4.0: 21步全链路已就绪。新增 special_lagnas/vimsopaka/varga_extended/karaka_jh/avasthas 五个模块。modules.congregation + modules.vivah_saham + antardasha + avasthas + vimsopaka 已就绪。Transit分析时必须输出Actionable Output(时间段+行动类型+置信度),动态预测必须先检索案例。', } return report diff --git a/karaka_calculator.py b/scripts/karaka_calculator.py similarity index 100% rename from karaka_calculator.py rename to scripts/karaka_calculator.py diff --git a/special_lagnas.py b/scripts/special_lagnas.py similarity index 100% rename from special_lagnas.py rename to scripts/special_lagnas.py diff --git a/vimsopaka_calculator.py b/scripts/vimsopaka_calculator.py similarity index 100% rename from vimsopaka_calculator.py rename to scripts/vimsopaka_calculator.py diff --git a/skills/jyotish-engine-modules/SKILL.md b/skills/jyotish-engine-modules/SKILL.md index 022e52a5..2e75d79c 100644 --- a/skills/jyotish-engine-modules/SKILL.md +++ b/skills/jyotish-engine-modules/SKILL.md @@ -138,13 +138,15 @@ python3 scripts/karaka_calculator.py --mode bphs --planets "Sun:45.5,Moon:120.3, 在 `jyotish_engine.py` 中导入这些模块: ```python -from scripts.karaka_calculator import KarakaCalculator, KarakaMode -from scripts.special_lagnas import SpecialLagnasCalculator -from scripts.vimsopaka_calculator import VimsopakaCalculator -from scripts.avastha_calculator import AvasthaCalculator -from scripts.divisional_charts_extended import DivisionalChartsExtended +from karaka_calculator import KarakaCalculator, KarakaMode +from special_lagnas import SpecialLagnasCalculator +from vimsopaka_calculator import VimsopakaBalaCalculator +from avastha_calculator import AvasthaCalculator +from divisional_charts_extended import DivisionalChartsCalculator ``` +> **注意**:这 5 个模块已整合到主仓库的 `scripts/` 目录中,与引擎一起维护。本 Skill 的 `scripts/` 副本仅作为独立分发包。 + ## 验证测试 ```bash