Overview

The package layout, the type system, and how to read this reference.

The Python package is a typed wrapper around the Rust core: computation happens in Rust, while the Python side provides a strongly typed API of dataclasses and StrEnums with zero external dependencies.

This section is the complete Python API reference — every function, class and method has its own entry.

Install

pip install x-iztro

Requires Python 3.10 or newer. The distribution ships a precompiled native extension (an abi3-py310 wheel), so installing needs no Rust toolchain.

StrEnum works on 3.10 too

enum.StrEnum only entered the standard library in 3.11. On 3.10 x_iztro.enums falls back automatically to the equivalent class StrEnum(str, Enum) implementation — the members are still both strings and completion targets, and the two versions behave identically.

Your first chart

from x_iztro import Astro

chart = Astro().by_solar("2000-8-16", 2, "female", language="en-US")  # 2 = Tiger hour (03:00–05:00)

print(chart.solar_date, chart.lunar_date)
# 2000-8-16 二〇〇〇年七月十七

soul = chart.palace("soulPalace")
print(" ".join(s.name for s in soul.major_stars))
# emperor

lunar_date is a Chinese-numeral lunar date string and stays Chinese under every language: 二〇〇〇年七月十七 is the 17th day of the 7th lunar month of 2000.

Package layout

ModuleContentsPage in this reference
x_iztro.AstroThe main charting classCharting entries
x_iztro.modelsThe Astrolabe, Palace, Star, Horoscope, ChartConfig and related dataclassesThe four pages from Astrolabe object onward
x_iztro.enumsStrEnums for every language-independent key, plus the GenderType, LanguageType, TimeIndexType and other type aliasesData tables, further down this page
x_iztro.queryLightweight queries for the zodiac animal, sign and Soul palace major starsLightweight queries
x_iztro.utilsIndex arithmetic, brightness and mutagen lookupsUtilities
x_iztro.starStar placement from birth dataStar placement
x_iztro.dataStar and stem/branch tables, ordering constantsData tables
x_iztro.i18nTwo-way lookup between keys and translationsTranslation
x_iztro.pluginAttaching custom methods to the astrolabe classExtending the astrolabe

models is an aggregation layer: Astrolabe actually lives in x_iztro.astrolabe, Palace in x_iztro.palace, Star in x_iztro.star_object, Horoscope in x_iztro.horoscope, ChartConfig in x_iztro.config and SurroundedPalaces in x_iztro.surpalaces. Importing from the x_iztro top level or from x_iztro.models gets you the same objects; take whichever you prefer.

Type aliases

x_iztro.enums holds a handful of Literal aliases whose job is to make your editor flag a wrong argument immediately:

AliasDefinition
GenderTypeLiteral["male", "female"]
LanguageTypeLiteral["zh-CN", "zh-TW", "en-US", "ja-JP", "ko-KR", "vi-VN"]
TimeIndexTypeLiteral[0, 1, …, 12]
StarTypeLiteralLiteral["major", "soft", "tough", "adjective", "flower", "helper", "lucun", "tianma"]
ScopeLiteralLiteral["origin", "decadal", "yearly", "monthly", "daily", "hourly"]

They are annotations only and validate nothing at runtime — the real value checking happens in the core, which raises IztroError on an illegal value.

Enums are the keys

Every enum in x_iztro.enums is a StrEnum whose value is the language-independent key, so it compares directly against the *_key fields on the data objects:

from x_iztro import MajorStar, PalaceName

soul = chart.palace(PalaceName.SOUL)
print(soul.major_stars[0].key == MajorStar.ZIWEI)
# True

Being StrEnums, string literals work just as well — chart.palace("soulPalace") and chart.palace(PalaceName.SOUL) are equivalent. The enums earn their keep through IDE completion and spell checking.

Test on key, never on name

star.name varies with the charting language (紫微 on a Chinese chart, emperor on an English one); star.key is ziweiMaj under any language. Every predicate should rest on the *_key fields or on the built-in predicate methods.

The data objects are immutable

Astrolabes, palaces and stars are all frozen=True dataclasses whose fields cannot be assigned after construction. When you need a variant, use a method that returns a new object, such as chart.rearranged(...).

try:
    chart.solar_date = "2001-1-1"
except Exception as e:
    print(type(e).__name__, e)

Output

FrozenInstanceError cannot assign to field 'solar_date'

Immutability lets a chart travel safely between analysis functions, go into a cache and be shared across threads, without worrying that a change in one place will affect another.

How to read an entry

Every API entry is organized into the same eight sections:

Purpose — one sentence on what it does
Zi Wei meaning — the concept it corresponds to in Zi Wei Dou Shu (omitted for purely engineering functions)
Signature — lifted verbatim from the source
Parameters — name, type, whether required, default, description
Return value — type and structure
Example — a snippet you can run as-is
Output — the real result of running that example
Edge cases and pitfalls — empty values, out-of-range input, configuration effects, interactions with other APIs

Examples all use the same chart — a female born 16 August 2000 in the Tiger hour (by_solar("2000-8-16", 2, "female")) — so they can be compared across pages. The full data for that chart is on the data model.

Every example on these English pages charts in en-US, so the display values in the output blocks are the English translations. Changing the language changes only those display strings; the *_key identifiers and the results of every predicate method stay the same.

On this page