# naturalstupid/pyjhora architecture

> Architecture diagram of the GitHub repository naturalstupid/pyjhora, generated by GitDiagram from its file tree, README and a sample of source files (last updated 2026-06-25). It is an AI-made overview: check details against the source.

- Interactive diagram: https://gitdiagram.com/naturalstupid/pyjhora
- Repository: https://github.com/naturalstupid/pyjhora

## Overview

1. **Overall shape**
   JHora is a Python package, not a single app: the core is an astrology computation engine, with a PyQt6 UI layered on top. The repository is organized around domain modules for panchanga, horoscope charts, dhasa systems, compatibility, prediction, and transit calculations.

2. **Core computation boundary**
   The main computational boundary is `jhora.panchanga.drik` plus related panchanga modules. This layer computes time- and location-based astronomical values such as sunrise/sunset, tithi, nakshatra, yogam, karana, lunar months, special lagnas, planet positions, eclipse dates, and entry/transit events. Most higher-level horoscope features depend on these outputs.

3. **Ephemeris and astronomical data**
   Planetary calculations depend on Swiss Ephemeris and the bundled ephemeris files under `src/jhora/data/ephe`. The README explicitly notes that accuracy is driven by the installed Swiss Ephemeris data. These files are a key external data dependency and are required for the core math to work.

4. **Horoscope chart subsystem**
   `jhora.horoscope.chart` builds on the panchanga layer to produce chart-centric outputs: rāśi/divisional charts, bhava houses, arudhas, ashtakavarga, yogas, doshas, strengths, sphutas, and relationship/aspect tables. This is the central analysis layer for horoscope interpretation and is where most chart-derived data is assembled.

5. **Dhasa engines**
   `jhora.horoscope.dhasa` is split into `graha`, `raasi`, `annual`, and `sudharsana_chakra` subpackages. Each module implements a specific dhasa-bhukti system and shares common inputs like planetary positions, nakshatra, divisional chart context, and configured year-duration rules. This subsystem is structurally separate from chart computation, but it consumes chart results heavily.

6. **Transit, prediction, and compatibility**
   Three adjacent analysis subsystems sit on top of the core chart data:
   - `match` for marriage compatibility tables and scoring,
   - `prediction` for rule-based general/longevity-style interpretations,
   - `transit` for tajaka, sahams, and annual/monthly/60-hour transit analysis.
   These are downstream consumers of the same horoscope state, but each has its own domain rules.

7. **Place and calendar data**
   Location lookup is handled by `place_db.py` and data files such as CSV/SQLite/DB place databases in `src/jhora/data`. The README notes support for multiple engines: CSV, pickle, and SQLite. Location data feeds latitude/longitude/time zone/elevation into panchanga and chart computations, so place resolution is a first-class dependency, not just UI input.

8. **Configuration and constants**
   `config.py`, `const.py`, and `_package_info.py` define package-wide modes and defaults such as ayanamsa behavior, node handling, chart options, and feature flags. This is an important boundary because many algorithms are parameterized by global configuration rather than hardcoded behavior.

9. **UI layer**
   `jhora.ui` contains multiple independent PyQt widgets rather than a single monolithic interface. The main surfaces are `horo_chart_tabs.py` for the full multi-tab experience, `panchangam.py` for one-page panchanga, `vedic_calendar.py`, `match_ui.py`, `vedic_clock.py`, `vratha_finder.py`, and chart-style dialogs. These widgets are presentation-only clients of the computation layer.

10. **Internationalization and resource files**
   The `lang` directory holds multilingual strings and message catalogs in English, Tamil, Telugu, Hindi, Kannada, and Malayalam. UI text and some output labels are driven from these resources, so language selection is a presentation concern that does not alter the underlying calculations.

11. **Static reference datasets**
   The package ships multiple domain datasets: marriage compatibility tables, festival CSVs, pancha pakshi data, geonames place data, user/factory settings, and documentation exports. These files are part of runtime behavior, not just documentation, because many calculations and lookups are table-driven.

12. **Testing and verification**
   `src/jhora/tests` contains a substantial test suite, including book-exercise baselines and regression outputs. The README calls out thousands of tests and special baseline JSON files. Architecturally, this is important because the project treats numerical correctness and compatibility with published astrology references as a primary quality gate.

13. **Packaging and runtime model**
   The repo is packaged as a Python library with `pyproject.toml`, `requirements.txt`, and `src/jhora/setup.py`. At runtime, it is intended both for direct library use and for launching PyQt widgets. There is also an MCP server wrapper mentioned in the README, which positions the library as a backend computation engine for other tools.

14. **Key dependency flow**
   The main data flow is: place/date/time input enters the UI or API, panchanga/drik computes astronomical state, chart modules derive horoscope structures, and then dhasa/prediction/match/transit modules interpret those structures. Output is rendered in UI tabs, dialogs, or exported reports/PDFs, with tests validating the same pipeline against reference examples.

Main entry points: [`src/jhora/horoscope/chart/charts.py`](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/chart/charts.py) (Charts), [`src/jhora/panchanga/drik.py`](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/panchanga/drik.py) (Drik), [`src/jhora/ui/horo_chart_tabs.py`](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/horo_chart_tabs.py) (Horoscope UI), [`src/jhora/lang/msg_strings_en.txt`](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/lang/msg_strings_en.txt) (Lang pack)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_core["Core math"]
  node_place_db[("Place DB<br/>location lookup<br/>[place_db.py]")]
  node_drik["Drik<br/>panchanga engine<br/>[drik.py]"]
  node_panchanga_misc["Panchanga<br/>calendar modules<br/>[eclipse.py]"]
end

subgraph group_analysis["Horoscope analysis"]
  node_chart_core["Charts<br/>chart builder<br/>[charts.py]"]
  node_chart_factors["Chart factors<br/>chart analysis<br/>[house.py]"]
  node_dhasa_graha["Graha dhasa<br/>dhasa systems<br/>[vimsottari.py]"]
  node_dhasa_raasi["Raasi dhasa<br/>dhasa systems<br/>[narayana.py]"]
  node_dhasa_annual["Annual dhasa<br/>dhasa systems<br/>[mudda.py]"]
  node_sudharsana["Sudharsana<br/>chakra dhasa"]
  node_match["Match<br/>compatibility<br/>[compatibility.py]"]
  node_prediction["Prediction<br/>rules engine<br/>[general.py]"]
  node_transit["Transit<br/>[tajaka.py]"]
end

subgraph group_ui["UI layer"]
  node_horo_ui["Horoscope UI<br/>main UI<br/>[horo_chart_tabs.py]"]
  node_panchangam_ui["Panchangam UI<br/>calendar UI<br/>[panchangam.py]"]
  node_match_ui["Match UI<br/>compatibility UI<br/>[match_ui.py]"]
end

subgraph group_data["Runtime data"]
  node_lang["Lang pack<br/>localization<br/>[msg_strings_en.txt]"]
  node_ephe[("Ephemeris data<br/>astronomy data<br/>[sepl_00.se1]")]
  node_places_data[("Place data<br/>lookup data")]
end

subgraph group_packaging["Package/runtime"]
  node_config["Config<br/>settings<br/>[config.py]"]
  node_const["Constants<br/>[const.py]"]
  node_pkginfo["Package info<br/>metadata<br/>[_package_info.py]"]
end

node_config -->|"modes"| node_drik
node_const -->|"constants"| node_drik
node_pkginfo -.->|"launch info"| node_horo_ui
node_places_data -->|"lookup"| node_place_db
node_place_db -->|"coords"| node_drik
node_ephe -->|"ephemeris"| node_drik
node_drik -->|"calendar state"| node_panchanga_misc
node_drik -->|"inputs"| node_chart_core
node_panchanga_misc -->|"derived values"| node_chart_core
node_chart_core -->|"structure"| node_chart_factors
node_chart_core -->|"chart state"| node_dhasa_graha
node_chart_core -->|"chart state"| node_dhasa_raasi
node_chart_core -->|"chart state"| node_dhasa_annual
node_chart_core -->|"chart state"| node_sudharsana
node_chart_factors -->|"interpret"| node_prediction
node_chart_core -->|"compatibility inputs"| node_match
node_chart_core -->|"baseline"| node_transit
node_lang -->|"strings"| node_horo_ui
node_lang -->|"strings"| node_panchangam_ui
node_lang -->|"strings"| node_match_ui
node_horo_ui -->|"invoke"| node_chart_core
node_horo_ui -->|"show results"| node_prediction
node_horo_ui -->|"show results"| node_transit
node_panchangam_ui -->|"compute"| node_drik
node_match_ui -->|"score"| node_match

click node_config "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/config.py"
click node_const "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/const.py"
click node_pkginfo "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/_package_info.py"
click node_place_db "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/place_db.py"
click node_drik "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/panchanga/drik.py"
click node_panchanga_misc "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/panchanga/eclipse.py"
click node_chart_core "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/chart/charts.py"
click node_chart_factors "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/chart/house.py"
click node_dhasa_graha "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/graha/vimsottari.py"
click node_dhasa_raasi "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/raasi/narayana.py"
click node_dhasa_annual "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/annual/mudda.py"
click node_sudharsana "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/sudharsana_chakra.py"
click node_match "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/match/compatibility.py"
click node_prediction "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/prediction/general.py"
click node_transit "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/transit/tajaka.py"
click node_horo_ui "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/horo_chart_tabs.py"
click node_panchangam_ui "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/panchangam.py"
click node_match_ui "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/match_ui.py"
click node_lang "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/lang/msg_strings_en.txt"
click node_ephe "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/data/ephe/sepl_00.se1"
click node_places_data "https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/data/geonames_places_5k.db"

classDef toneNeutral fill:#f8fafc,stroke:#334155,stroke-width:1.5px,color:#0f172a
classDef toneBlue fill:#dbeafe,stroke:#2563eb,stroke-width:1.5px,color:#172554
classDef toneAmber fill:#fef3c7,stroke:#d97706,stroke-width:1.5px,color:#78350f
classDef toneMint fill:#dcfce7,stroke:#16a34a,stroke-width:1.5px,color:#14532d
classDef toneRose fill:#ffe4e6,stroke:#e11d48,stroke-width:1.5px,color:#881337
classDef toneIndigo fill:#e0e7ff,stroke:#4f46e5,stroke-width:1.5px,color:#312e81
classDef toneTeal fill:#ccfbf1,stroke:#0f766e,stroke-width:1.5px,color:#134e4a
class node_place_db,node_drik,node_panchanga_misc toneBlue
class node_chart_core,node_chart_factors,node_dhasa_graha,node_dhasa_raasi,node_dhasa_annual,node_sudharsana,node_match,node_prediction,node_transit toneAmber
class node_horo_ui,node_panchangam_ui,node_match_ui toneMint
class node_lang,node_ephe,node_places_data toneRose
class node_config,node_const,node_pkginfo toneIndigo
```

## Components

### Core math

Time, place, and astronomical computations used by all higher layers.

- [Place DB](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/place_db.py): location lookup · Resolves location, timezone, and elevation data. · `src/jhora/place_db.py`
- [Drik](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/panchanga/drik.py): panchanga engine · Primary astronomical and calendar computation engine. · `src/jhora/panchanga/drik.py`
- [Panchanga](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/panchanga/eclipse.py): calendar modules · Eclipse, Hijri, Paksha, Vratha, and related panchanga calculations. · `src/jhora/panchanga/eclipse.py`

### Horoscope analysis

Chart construction and downstream interpretive systems.

- [Charts](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/chart/charts.py): chart builder · Builds rasi and divisional chart structures from panchanga state. · `src/jhora/horoscope/chart/charts.py`
- [Chart factors](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/chart/house.py): chart analysis · House, arudha, ashtakavarga, strength, sphuta, yoga, and dosha logic. · `src/jhora/horoscope/chart/house.py`
- [Graha dhasa](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/graha/vimsottari.py): dhasa systems · Planet-based dhasa engines such as vimsottari and yogini. · `src/jhora/horoscope/dhasa/graha/vimsottari.py`
- [Raasi dhasa](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/raasi/narayana.py): dhasa systems · Sign-based dhasa engines such as narayana, kalachakra, and sudasa. · `src/jhora/horoscope/dhasa/raasi/narayana.py`
- [Annual dhasa](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/annual/mudda.py): dhasa systems · Yearly timing systems including mudda and patyayini. · `src/jhora/horoscope/dhasa/annual/mudda.py`
- [Sudharsana](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/dhasa/sudharsana_chakra.py): chakra dhasa · Sudharsana chakra timing and progression analysis. · `src/jhora/horoscope/dhasa/sudharsana_chakra.py`
- [Match](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/match/compatibility.py): compatibility · Marriage compatibility scoring and table lookup. · `src/jhora/horoscope/match/compatibility.py`
- [Prediction](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/prediction/general.py): rules engine · General and longevity interpretation rules. · `src/jhora/horoscope/prediction/general.py`
- [Transit](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/horoscope/transit/tajaka.py): tajaka/transit · Tajaka, saham, and transit-based annual analysis. · `src/jhora/horoscope/transit/tajaka.py`

### UI layer

PyQt presentation surfaces over the computation engine.

- [Horoscope UI](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/horo_chart_tabs.py): main UI · Main multi-tab chart and analysis workspace. · `src/jhora/ui/horo_chart_tabs.py`
- [Panchangam UI](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/panchangam.py): calendar UI · Panchanga, calendar, and time-oriented presentation surfaces. · `src/jhora/ui/panchangam.py`
- [Match UI](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/ui/match_ui.py): compatibility UI · User interface for compatibility and match analysis. · `src/jhora/ui/match_ui.py`

### Runtime data

Bundled ephemeris, lookup tables, and localized resources.

- [Lang pack](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/lang/msg_strings_en.txt): localization · Multilingual UI strings and output labels. · `src/jhora/lang/msg_strings_en.txt`
- [Ephemeris data](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/data/ephe/sepl_00.se1): astronomy data · Swiss Ephemeris files used by the core astronomical engine. · `src/jhora/data/ephe/sepl_00.se1`
- [Place data](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/data/geonames_places_5k.db): lookup data · Bundled CSV/DB place databases for geocoding and locality lookup. · `src/jhora/data/geonames_places_5k.db`

### Package/runtime

Library entrypoints, configuration, and packaging metadata.

- [Config](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/config.py): settings · Package-wide modes, defaults, and feature flags. · `src/jhora/config.py`
- [Constants](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/const.py): constants · Shared symbolic values and global calculation switches. · `src/jhora/const.py`
- [Package info](https://github.com/naturalstupid/pyjhora/blob/main/src/jhora/_package_info.py): metadata · Package version and distribution metadata. · `src/jhora/_package_info.py`

## Connections

- Config → Drik: modes · Configuration alters astronomical and calendar calculations.
- Constants → Drik: constants · Shared constants parameterize the core engine.
- Package info → Horoscope UI: launch info · Package metadata supports runtime/package presentation.
- Place data → Place DB: lookup · Location engines are backed by bundled place datasets.
- Place DB → Drik: coords · Resolved latitude, longitude, timezone, and elevation feed panchanga math.
- Ephemeris data → Drik: ephemeris · Swiss Ephemeris files drive planetary and lunar calculations.
- Drik → Panchanga: calendar state · Derived astronomical state powers secondary panchanga modules.
- Drik → Charts: inputs · Charts are built from panchanga and planetary outputs.
- Panchanga → Charts: derived values · Calendar and event calculations feed chart assembly.
- Charts → Chart factors: structure · Core chart data is analyzed into houses, yogas, strengths, and related factors.
- Charts → Graha dhasa: chart state · Graha dhasa systems consume planetary and nakshatra context.
- Charts → Raasi dhasa: chart state · Raasi dhasa systems consume sign and divisional chart context.
- Charts → Annual dhasa: chart state · Annual dhasa systems reuse horoscope-derived inputs.
- Charts → Sudharsana: chart state · Sudharsana analysis is computed from the horoscope baseline.
- Chart factors → Prediction: interpret · Rule-based prediction layers consume chart-derived factors.
- Charts → Match: compatibility inputs · Compatibility scoring uses the same horoscope state.
- Charts → Transit: baseline · Transit analysis is anchored to the natal chart.
- Lang pack → Horoscope UI: strings · UI labels and messages are localized from resource files.
- Lang pack → Panchangam UI: strings · Calendar views use localized text resources.
- Lang pack → Match UI: strings · Compatibility UI uses localized text resources.
- Horoscope UI → Charts: invoke · Main UI triggers chart generation and analysis workflows.
- Horoscope UI → Prediction: show results · Predictions are surfaced in the main workspace.
- Horoscope UI → Transit: show results · Transit analysis is surfaced in the main workspace.
- Panchangam UI → Drik: compute · Panchanga views directly invoke core calculations.
- Match UI → Match: score · Compatibility UI drives the match engine.
