Changelog

Changelog

All four packages version in lockstep. caelus-delineations-pd ships on its own semver. Numbers are as measured at release time; current figures live in accuracy.json and on Validation.

v0.25.0 — Era packs to 3000 BCE, 27 fact kinds, MultiWheel

2026-09-26

Engine (caelus)

  • Era packs. loadNodeData loads Chebyshev slabs {body}_cheb.classical.json (JPL Horizons / DE441) covering 3000 BCE to 1000 CE for the Sun (via Earth's slab), the Moon, Mercury, Venus, Mars, Jupiter, and Saturn. Each slab ends at its modern pack's first instant. engineCapabilities reports the chained span, −2998 to 3000. Bodies without a classical pack are omitted and listed in chart.unavailable. The seven slabs ship in the npm tarball (check-tarball gates them), so the tarball grows to about 130 MB unpacked, 55 MB packed.
  • interpretationContext grows to 27 fact kinds. New atoms: angleContact, transitHouse, station, return, lunation, solarPhase, compositeAspect, degree, with matching selectors (hasDegree included). Node aspects and the node as a transit target now project; peregrine is marked on placement atoms. enrichContextOptions projects transit houses, stations, returns, and lunations by default.
  • Draconic. draconicLongitude / draconicChart re-zero the zodiac at the Moon's ascending node (true node by default).
  • VERSION. Runtime string constant, asserted equal to package.json.
  • Vector-mode sky projection. skyCamera, radialScale, and skyProjector (plus dirFromAzAlt) for consumers that draw rather than place pixels. Python mirrors (sky_camera, radial_scale, sky_project); the skyview golden pins the pair.
  • sceneNote. Optional extra SCENE line on skyView (place, weather, foreground). It lands in prompt and renderPlan.background.prompt; placements do not change.

Corpus (caelus-corpus, unpublished)

Original essays written against the engine's fact atoms, lazy-loaded in the Playground Reading tab (natal / conditions / degrees / transits / timing / relationship subpaths). caelus-delineations-pd remains the published npm corpus.

Delineations (caelus-delineations-pd 0.1.6)

The caelus peer range widens to >=0.24.0 <0.26 so the corpus installs beside 0.25.0. Extractors now repair OCR damage and section bleed instead of quoting into the next chapter, and validation fails when an OCR token survives into a passage. Alan Leo's Key is quarantined and Heindel is re-sourced from the Rosicrucian Fellowship HTML. 372 passages ship.

Wheel (caelus-wheel)

  • MultiWheel: a rings API, up to four charts. Kundli and the Playground BiWheel stay.
  • EphemerisGraph accepts band / marks / cursor / accent. Gridline, band, mark, and cursor coordinates round to 0.1, as the polylines already did, so the SVG is byte-identical on arm64 and x86-64.
  • PLATE_TOKENS, PLATE_THEME, PLATE_BODY_INKS: an optional ink palette for widget figures.

Playground widgets (caelus-widgets)

Interactive figures mounted in the Workspace playground (no Encyclopedia chrome): house comparator, sky→wheel derivation, sect flip, retrograde scrub, and aspect dial. Figures accept an optional theme so the playground can pass WHEEL_THEME. DerivationFigure accepts openingAim for a scenic VIEW pre-roll before SKY, and overlays to name bodies from t = 0 then light the great cross (ecliptic × horizon), then figures, signs, and houses. With overlays the camera keeps tilting from SPHERE through the fold, then flattens slowly onto the page as each mark lerps onto the natal wheel. PlateConsole accepts snapOnRelease={false} for a free-stop scrub; a drag that leaves the rule keeps the pointer and does not start a text selection. More than six stations stack on two rows so the labels do not collide. Overlay glyphs take a hairline halo (and follow theme when one is passed) so counters stay open in dark mode.

Site (apps/web)

  • Playground Reading tab (the natal report, and the compare reading when a partner is present) lazy-loads the B5 conditions and B6 degree batches via caelus-corpus/conditions and caelus-corpus/degrees, alongside natal, transits, and timing.
  • Home page: below the proof cards, a live New York event sky (read-only stamp), a pre-generated plate composited with skyProjector, a derivation morph that folds into a large chart: named bodies at VIEW, then the ecliptic and horizon as the great cross on the still photograph, then constellation, zodiac, and house overlays, a continuous tilt through SPHERE, a slow flatten that carries each mark onto the natal wheel. The plate stays under the figure through WHEEL. The natal wheel under the stage stays put after the fold. Transport (previous, play, pause, next) sits at the left of the scrub, on the rule. Then the ecliptic strip and a Compute-a-chart sample synced to the same instant.

v0.24.1 — Ship the complete tarball (wide planet packs restored)

2026-08-15

The 0.24.0 npm tarball omitted four advertised data packs (mercury_cheb, venus_cheb, jupiter_cheb, earth_cheb); installs silently fell back to VSOP87D and the 1000–3000 accuracy did not apply from the package. This release ships all 25 advertised packs. No API changes. Use 0.24.1; 0.24.0 is deprecated on npm.

v0.24.0 — Canonical output and the 1000–3000 tier

2026-08-15

Two headline changes. Canonical mode gives the engine integer, hashable, precision-honest output — content-addressable charts that are bit-identical across machines, browsers, and languages. And the validated range widens from 1850–2150 to 1000–3000, with every solar-system body now carrying a Chebyshev pack fit to JPL Horizons (DE441) across the span.

Canonical mode (caelus)

Floating point is deterministic run-to-run but not across platforms (IEEE 754 pins arithmetic, not the transcendentals), not in serialized form, and not at rounding boundaries. Canonical mode closes all three:

  • canonicalChart(chart, { grid }) quantizes every continuous quantity to integers on a declared grid — arcsec (default), milliarcsec, centideg, dms triples, or accuracy (each body snapped to its measured validated accuracy). One rounding rule (round half toward +infinity), identical in TypeScript and Python. Sign, house, dignities, retrograde and the aspect list are then re-derived from the quantized integers, so displayed numbers and derived facts cannot disagree.
  • chartDigest(chart) — a dependency-free SHA-256 over the canonical encoding gives content-addressable charts for caching, dedupe, and provenance receipts. The encoding throws on any non-integer, so a digest proves full quantization. TS and Python digests match byte for byte (pinned by the tolerance-free canonical-golden suite).
  • Remainder sets (canonicalChartWithRemainders, composeRemainders, nearBoundary): the canonical payload is the base layer, an optional sidecar keeps the discarded sub-quantum residue as integers — composable back to the finer grid exactly, and nearBoundary reports the leaves that sit within a stated margin of a rounding boundary (the places cross-platform drift could flip a sign, house, or aspect).
  • MCP: natal_chart, current_sky, returns, and parans accept output: "canonical" (+ grid, + remainders), returning the all-integer payload and its digest.

The 1000–3000 tier (caelus)

The validated range widens from 1850–2150 to 1000–3000. Every solar-system body — the eight planets, Earth, Pluto, the Moon, Chiron, and the five asteroids — now carries a Chebyshev pack fit to JPL Horizons (DE441) across the span, and measures sub-arcsecond against JPL on the frame-free basis (sun 0.03″, the majors 0.02–0.12″, Pluto 0.015″, the small bodies 0.04–0.16″). See docs/range-expansion.md for the measured tables.

Engine (caelus)

  • Wide packs for everything. fit_planet.py mints Mercury, Venus, Earth, Mars, Jupiter, Saturn, Uranus and Neptune; fit_smallbody.py the asteroids and Chiron; fit_pluto.py Pluto; fit_moon.py the Moon. Packs supersede the VSOP87D / analytic series wherever they load. Earth is packed too — it is the observer, and its own VSOP error was the floor under every geocentric body (Mars read 6.75″ until Earth was packed; 0.088″ after).
  • Fitted vs validated. engineCapabilities reports each pack's real fitted span separately from the validated span. The majors, Pluto and the Moon validate 1000–3000; the small bodies 1600–2484 (the widest window Horizons serves them). A body outside its pack lands in Chart.unavailable; the unvalidated fallback is not served.
  • Aberration latitude term. Annual aberration now corrects ecliptic latitude as well as longitude (Meeus eq. 23.3), fixing a large error for high-inclination bodies: Pallas read 13.3″ off against JPL in latitude alone, Pluto ~4.6″. Every packed body now measures under 1″ in the core band.
  • Delta-T warnings for ancient dates. Chart.warnings states the delta-T split per chart: at 1000 CE sigma is ~76 s, smearing the angles ~0.32° and the Moon ~0.7′ while the slow bodies hold. "Validated to 1000–3000" is a TT position claim; the input clock is fuzzier than the engine for ancient dates.

Also in this release

  • engineCapabilities (caelus): runtime introspection — each body's source, fitted span and validated span, the headline band, and the delta-T uncertainty per epoch. Chart.warnings reports per-chart validity and delta-T uncertainty.
  • intp_apog: the interpolated ("natural") lunar apogee as a first-class point.
  • SkyView photometry: brightness, obstruction and prompt-style controls.
  • Latitude-aware constraints and spatial (3D) aspect separation: the constraint compiler leaves the circle; aspects can separate in 3D.
  • Parallels of declination and out-of-bounds as first-class fact kinds; the selector layer now covers every fact kind, with context-fed selector kinds and a Brihat Jataka nakshatra corpus.
  • MCP: a natal_reading prompt, the parans tool, exotic-provenance anchors, and the scripted MCP Registry push.

Notes for consumers

  • Canonical digests change. Latitude/declination for Pluto and the small bodies moved with the aberration fix, and every geocentric body moved with the packs, so previously issued accuracy-grid and canonical digests for those bodies will differ; the new figures are the corrected ones.
  • The hosted edge API keeps a narrower window (its embedded Moon tier, 1920–2080); its out-of-range error now names that tier and points at the engine's full 1000–3000 validation.
  • The full Moon pack (1000–3000) is repo-only, like the existing full tier; the npm tarball still ships the embedded 1920–2080 Moon plus every wide planet/Pluto/asteroid pack.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.24.0. caelus-delineations-pd ships at 0.1.3 (peer range >=0.20.1 <0.24).

v0.23.0 — Synthetic ephemeris

2026-06-21

Imaginary bodies that move over time: placement, periodic, and Kepler tiers; register on Engine for transits, returns, and SkyView with authored render attributes (size, magnitude, colour).

Engine (caelus)

  • syntheticPositions / syntheticEphemeris: world-frame position over time, with optional observer for geocentric apparent motion and retrograde.
  • registerSyntheticSystem: drop authored bodies into a real Engine via registerSource; returns, skyView, and the rest work unchanged.
  • Engine.registerSource / registerRender: runtime body registration and SkyView appearance attributes.
  • SkyView: render opts and engine-registered attributes flow into body pixels and the image prompt.

MCP (caelus-mcp)

  • synthetic_validate, synthetic_positions, synthetic_sky_view (tool count 31 → 34).

Web

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.23.0. caelus-delineations-pd remains at 0.1.2 (dependency range ^0.23.0).

v0.22.0 — Sky View

2026-06-21

Sky View: frame the visible sky from a place and moment as a pixel-precise prompt for AI image generation. Caelus computes the truth (positions, sizes, brightness, phase); it does not render images.

Engine (caelus)

  • skyView(): project the visible sky into image pixels for a given observer, aim (azimuth + altitude), lens preset, and image size. Returns each in-frame body's pixel position, apparent size, magnitude with a brightness cue, the Moon's phase orientation (which way the crescent points), twilight stage and limiting magnitude, the horizon row, bright bodies just outside the frame, the celestial pole, and a ready-to-use image prompt.
  • Dark sky and stars: a bortle dark-sky class, the Milky Way band (galactic plane projected through precession), and a deep star field of 8,920 naked-eye stars to magnitude 6.5 (data/fixed_stars_deep.json, opt-in, node-loaded). The complete field is pinned at exact pixels for dark scenes.
  • Overlays: project the ecliptic, the zodiac signs, the house cusps and angles, and the constellation figures (data/constellations.json) as exact-pixel annotation layers.
  • skyViewSequence(): step the same frame through time for animation, with the sidereal rotation per frame about the celestial pole. Each frame is a complete, physically exact spec. New SkyView golden checks pin the geometry.
  • renderPlan: a machine-readable hybrid-render contract on every result. A body-free background-plate prompt (for an image model) plus the computed layers (bodies, stars, Milky Way, overlays) to composite locally, an animation strategy, and grading notes. The model supplies atmosphere; Caelus supplies the physically correct objects.

MCP (caelus-mcp)

  • sky_view and sky_view_sequence tools (tool count 29 → 31): frame the sky and plan animation timelines over stdio and the hosted endpoint. sky_view takes bortle, deep_field, and overlays.

Web

  • Playground "Sky View" tab: a live frame builder with aim, lens, and image controls, a play/scrub time control, Bortle and overlay toggles, an SVG preview, and a copy-to-clipboard prompt. The cited reading now sits at the foot of the chart panel rather than leading it.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.22.0. caelus-delineations-pd remains at 0.1.2 (dependency range ^0.22.0).

v0.21.0 — per-body planet colors on ChartWheel

2026-06-20

Feature release across the four core packages: caelus-wheel gains optional planetColors on WheelTheme for per-body glyph and position-tick tints; the Playground wires them through CSS tokens aligned with AstroMap/EphemerisGraph.

Wheel (caelus-wheel)

  • WheelTheme.planetColors: optional Record<string, string> keyed by body name; glyph fill and position tick stroke use it, falling back to planetText when omitted.
  • Render test coverage for partial overrides.

Web

  • WHEEL_THEME: --wheel-planet-* CSS tokens; Moon and Saturn reuse mode-aware line colors for light/dark legibility.
  • Playground Facts tab stays inside page margins on wide viewports.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.21.0. caelus-delineations-pd remains at 0.1.2 (dependency range ^0.21.0).

corpus v0.1.2 — fix packaging so external installs resolve

2026-06-17

tsc (with rootDir: "." + resolveJsonModule) copies the corpus JSON to dist/data/ and dist/sources/, and the compiled dist/src/*.js import it from there (../data, ../sources). The published files shipped only dist/src plus the root data/sources, so those dist/-level JSON files were missing from the tarball and any external consumer hit ERR_MODULE_NOT_FOUND on import. The monorepo Playground was unaffected because the local build leaves the files in place. Surfaced wiring the corpus into a downstream app.

  • caelus-delineations-pd → 0.1.2: add dist/data and dist/sources to files. No corpus, API, or dependency changes. Verified by installing the packed tarball into a clean consumer and resolving a 24-entry reading.

corpus v0.1.1 — track caelus 0.20.1

2026-06-17

Corpus-only republish of caelus-delineations-pd so a single caelus resolves for consumers. The 0.1.0 on npm pins caelus ^0.19.0, which excludes 0.20.x; the range was corrected to ^0.20.1 in the tree at v0.20.0/v0.20.1 but never shipped, because the version stayed at 0.1.0 and publish-if-missing skips a version already on the registry. Bumping to 0.1.1 ships the corrected range.

  • caelus-delineations-pd → 0.1.1: caelus dependency ^0.19.0 → ^0.20.1. No corpus or API changes — the star/lot/dignity selectors and the 334-passage set are unchanged. Validation green against caelus 0.20.1.
  • Core packages unchanged (still 0.20.1); this is a single-package patch.

v0.20.1 — fixed stars in embedded data

2026-06-17

Patch release across the four core packages: the HYG fixed-star catalog now ships in caelus/data-embedded, so starNames(), starConjunctions(), and Robson star:* interpretation atoms work in the browser and on edge without loadNodeData().

Engine (caelus)

  • data-embedded: bundles data/fixed_stars.json (~13 KB gzipped; embedded pack ~97 KB gzipped total).
  • npm files includes data/fixed_stars.json.

Web

  • Removed duplicate apps/web/lib/fixed-stars.json; Playground and hosted MCP use the catalog from embeddedData.
  • Data-tiers and corpus docs updated; embedded bundle size figures revised.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.20.1. caelus-delineations-pd remains at 0.1.0 (dependency range ^0.20.1).

v0.20.0 — diachronic/relational interpretation atoms

2026-06-17

A feature release across the four core packages: the interpretation layer now projects transits, synastry/composite geometry, time-lords, finer dignities, and Vedic structure as citable fact atoms; MCP and the Playground surface them with enriched briefs.

Engine (caelus)

  • Relational projection: interpretationContext() now emits transit, synastry, composite, time-lord, finer-dignity, nakshatra, varga, and yoga atoms with stable ids for auditCitations.
  • relational.ts: transitAspects, synastryAspects, synastryOverlays, compositePlacements.
  • interpretation-enrich.ts: enrichContextOptions (transits, time-lords, Vedic at a target instant) and enrichSynastryOptions.
  • New selectors: hasTransit, hasSynastry, hasComposite, hasTimelord, hasDignityFine, hasNakshatra, hasVarga, hasYoga.

MCP (caelus-mcp)

  • chart_facts: optional target_date and include_vedic enrich the brief with transits, time-lords, and sidereal structure.
  • synastry: returns ranked facts and a citable brief alongside the inter-chart geometry.

Web

  • Playground Reading and Facts tabs project enriched, citable atoms (transits and time-lords); the synastry compare panel adds synastry/composite atoms.
  • Public docs, features copy, and llms.txt updated for the enriched atom kinds.

CI

  • verify_tools: synastry oracle uses synastryAspects (matches non-aspectable body policy).

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.20.0. caelus-delineations-pd remains at 0.1.0 (dependency range updated to ^0.20.0).

v0.19.0 — interpretation corpus, star/lot atoms, and cited Playground readings

2026-06-16

A feature release across the four core packages plus the first npm publish of caelus-delineations-pd: a public-domain interpretation corpus, star and Hermetic-lot fact atoms, MCP chart_facts enrichment, canonical site facts sync, and a Playground tab that runs the corpus in-browser with clickable citations.

Engine (caelus)

  • Star and lot atoms: interpretationContext() accepts stars (from Engine.starConjunctions()) and lots (from Engine.lots()); new hasStar / hasLot selectors and salience weights for fixed-star conjunctions and the Part of Fortune and its companions.
  • Golden suite extended for lot projection wiring.

MCP (caelus-mcp)

  • chart_facts auto-enriches ephemeris charts with Fortune/Spirit lots and tight fixed-star conjunctions before building the brief.

Corpus (caelus-delineations-pd @ 0.1.0, first npm publish)

  • 334 passages from seven sources: planet-in-sign/house, aspects, rising sign, curated Robson fixed stars; compiled to InterpretationSources with a validation harness (npm test in the package).
  • publicDomainSources drops the segregated Llewellyn George gratis-not-pd cells; sources includes them.
  • Liber 777 correspondences table; manifest-driven fetch/extract pipeline in-repo.

Web

  • New guide: Building a corpus; Interpretation and Provenance added to the docs sidebar.
  • Canonical facts: scripts/sync-facts.mjs derives accuracy.json counts and claims anchors; web pages import apps/web/lib/facts.ts formatters.
  • Playground: in-browser cited reading from caelus-delineations-pd with curated clickable examples.

CI

  • caelus-delineations-pd build + validation harness gated in conformance.
  • facts:sync runs before lint:claims.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.19.0. caelus-delineations-pd publishes at 0.1.0.

v0.18.0 — interpretation, provenance, and the wider sky (27→29 MCP tools)

2026-06-15

A feature release across all four packages. The engine gains an interpretation layer (ranked, citable chart atoms), a provenance contract (realm, time certainty, and honest routing between ephemeris and compiler), eclipse geography, a Pluto barycenter Chebyshev pack that extends the validated range to 1850–2150, and counterfactual charts with legible diffs. The MCP server grows from twenty-seven to twenty-nine tools.

Engine (caelus)

  • Interpretation layer: interpretationContext() normalizes a chart into ranked, addressable atoms (placements, aspects with phase and strength, receptions, configurations, sect, dignities). interpret() runs a rule corpus with conflict detection; chartBrief() and auditCitations() ground LLM prose in those facts.
  • Provenance layer: realize() routes an anchored chart (realm, when, where) to ephemeris (chartAt), the geometric compiler (compileForm), or an honest refusal. Time certainty (exact, approximate, representative) damps Moon/angle salience in briefs; realmFraming() sets the interpretive tone.
  • Counterfactuals: counterfactual() perturbs a resolved chart (shift time, move place, or splice body longitudes); chartDiff() reports sign/house/aspect and angle changes without burying the edit in two full charts.
  • Eclipse geography: solarEclipseWhere, solarEclipseLocal, solarEclipseLimits, and lunarEclipseLocal report sub-solar points, path width, and local circumstances from the validated eclipse search.
  • Chart aspects now carry phase (applying/separating) and normalized strength on Chart.aspects.
  • Range expansion: Pluto fitted to JPL Horizons barycenter (body 9), not Charon-wobble body 999; validated 1850–2150 with Pluto ≤3.4″, mean Lilith ≤1.6″. HorizonsCache.ensure() now guards on cached body label, not just JD span.

MCP (caelus-mcp)

  • chart_facts: ranked facts plus a ready brief; structured when anchors, in-request anchors registry, realm, and constraints for archetypal or uncertain charts.
  • counterfactual_chart: birth chart perturbed with a legible diff (bodies, aspects gained/lost, angles).
  • natal_chart aspects include strength; sky_events reports eclipse geography.

Web

  • New guides: Interpretation, Provenance.
  • Docs, features, FAQ, and claims synced to twenty-nine MCP tools and the new surface.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.18.0.

v0.17.0 — fixed-star parans (Brady)

2026-06-15

A feature release across all four packages. The engine gains the fixed-star parans — the star-to-body half of the paranatellonta — extending the moving-body parans() that shipped in 0.16.0. Reads off the validated positions; no new ephemeris fits.

Engine (caelus)

  • starParans(engine, jd, lat, stars) finds the classic fixed-star parans of Brady's tradition: a catalog star and a moving body simultaneously on one of the four angles (rising, setting, or either meridian) within a stated tolerance, on a given day and latitude. A star's four angle crossings come analytically from its apparent RA/Dec and the sidereal-time condition (H=0 at the meridian, H=±H₀ at rise/set), inverted to UT through gast; body times reuse the existing rise/set path. starAngleTimes() exposes the per-star crossings. Standard 34′ refraction at rise/set, matching the engine's rise/set. Reference-first (astroengine.parans.star_parans), the TS port pinned by parans-golden (400 checks), with an oracle that a star's upper transit is when sidereal time equals its right ascension.

Web

  • The playground stars tab surfaces the tightest fixed-star parans (a bright star and a body on the angles at once, this day and latitude) alongside the longitude conjunctions.
  • The docs guides (charts, houses-and-zodiacs, hellenistic, vedic, derived, electional) are illustrated with server-rendered, build-time figures computed from one canonical sample natal, so the prose, code samples, and rendered output agree and the pages stay deterministic.
  • The home and features pages are refreshed: a linked proof strip of the validation numbers above the fold, the worked example promoted ahead of the package list, and a comparison against the other engines on /features.

All four npm packages (caelus, caelus-mcp, caelus-birth, caelus-wheel) and the caelus-engine PyPI package ship at 0.17.0.

v0.16.0 — chart synthesis: patterns, dignities, parans + search (22→27 MCP tools)

2026-06-15

A feature release across all four packages: the analytic synthesis layer (Roadmap Phase 4) and the mundane and search tools (Phase 4b). Everything reads off the validated positions and is pinned to the Python reference; no new ephemeris fits. The MCP server grows from twenty-two to twenty-seven tools.

  • detectPatterns() names the classical configurations as structured objects: T-squares, grand trines, grand crosses, yods, kites, mystic rectangles, and stelliums (by sign and by house). Reported patterns are maximal, so a grand cross hides the T-squares inside it and a kite its grand trine. Surfaced over MCP as aspect_patterns.
  • chartSignature() reduces a chart to plain counts: the element, modality, quadrant, and hemisphere distributions, the dominant element, modality, and sign, and the classical chart ruler. Surfaced over MCP as chart_signature.
  • dignityScore() and almuten() add the traditional five-fold essential dignities with William Lilly's weights (rulership +5, exaltation +4, triplicity +3, term +2, face +1; detriment -5, fall -4), reporting the breakdown, the running total, and a peregrine flag. The triplicity (Dorothean), term (Egyptian bounds), and face (Chaldean) tables are each pinned to a named authority. The MCP dignities payload now carries this weighted score.
  • parans() computes paranatellonta (co-angular bodies): pairs whose rise, set, or meridian crossings fall within a stated tolerance on a given day and latitude, the relationship behind Brady's fixed-star parans, computed here for the moving bodies. Longitude-independent; pinned by parans-golden.
  • Three search and mundane MCP tools over the existing math: similar_skies (when the sky most resembled a reference moment, by cosine similarity over a window), electional_search (rank moments in a window for a set of wanted aspects, optionally avoiding a void-of-course Moon), and cosmic_weather (a date's active configurations, stationing planets, and void-of-course Moon, with no birth chart or location needed).

Web

  • A hand-drawn Caelus sky-god mark (CaelusMark) after the Carnuntum altar, with a "Why the name Caelus?" note on /how-it-was-built, an off-the-chart 404 page, a faint watermark on the OpenGraph image, and an ASCII banner on caelus-mcp startup.
  • A homepage FAQ with FAQPage structured data, and an "MCP tools" call to action linking the tool catalog.

v0.15.0 — enriched chart bodies + API polish

2026-06-14

API-feedback polish across all four packages, prompted by an external review of the chart contract. No new techniques; this tightens what a chart returns and how its bodies are typed.

  • chart()/chartAt() now return enriched bodies (ChartBody): each carries its 1-based house (by the chart's cusps) and the dignities it holds in its sign, so library callers no longer recompute placement from cusps.
  • A body outside its fitted range (Chiron, opt-in asteroids before ~1850 or after ~2150) is now omitted from bodies and listed in the new Chart.unavailable[] rather than failing the whole chart; the analytic Sun–Pluto and nodes still compute. An absurd instant (a Julian Day passed where a calendar year belongs) still throws RangeError.
  • Chart.bodies is typed to match what a chart actually holds: the analytic core (AlwaysBody, Sun–Pluto and the nodes) is guaranteed and autocompleted, while Chiron and any opt-in extras read as ChartBody | undefined so the omission case must be handled. caelus-wheel's WheelChart/SphereChart accept the same optional bodies (they already filter absent ones before rendering).
  • New pure sign helpers: element(sign), modality(sign), quadrant(house). The dignities(body, sign) primitive moved to the chart module (same export from the package root).
  • Forgiving house-system input: normalizeHouseSystem() accepts any case, spaces or hyphens, and common aliases ("whole sign", "Placidus", "whole" all resolve), and the unknown-system error lists the valid ids. caelus-mcp's house_system accepts the same lenient strings.
  • caelus-mcp chart payloads surface per-body dignity (omitted when peregrine, to stay token-frugal).
  • fmtLon() (and the MCP formatter) normalize their argument, so an exact 360 or a small negative no longer renders an out-of-range sign.

v0.14.0 — Vedic completion + chat MCP App (18→22 MCP tools)

2026-06-14

A feature release across all four packages. The engine resolves the deferred Phase 2 techniques — the full Parashari varga set (adding hora D2 and the unequal trimsamsa D30), the Ashtottari dasha, the Kemadruma yoga, a lordship and graha-drishti layer with raja/dhana yogas and yogakarakas, and inter-planetary (mundane) primary directions — each pinned by the new validate_jyotish reference tier. The MCP server grows from eighteen to twenty-two tools, surfacing the whole Vedic layer over MCP: nakshatras, dasha (Vimshottari/Yogini/Ashtottari), vargas, and yogas; the directions tool gains an optional inter-planetary (mundane) block.

Web / chat MCP App (Roadmap Phase 3)

  • In-host chart renderer for the chat MCP App: apps/web/app/embed/chart, a chrome-free route that renders caelus-wheel's ChartWheel from a natal_chart/current_sky payload (read from the Apps-SDK host's window.openai.toolOutput, with a ?c=<base64 chart JSON> fallback for standalone use). Interpretation-free; the MCP payload feeds the wheel as-is. The server-side UI-resource wiring lands with the MCP layer. See docs/mcp-app.md.

Engine (caelus)

  • Trimsamsa (D30) divisional chart: the BPHS unequal five-band rule (odd signs Mars 5 / Saturn 5 / Jupiter 8 / Mercury 7 / Venus 5 -> their odd signs; even signs reversed -> their even signs). varga(lon, 30) and vargaChart(..., 30); vargas-golden pin plus a band oracle and a cited entry in the new Jyotish reference.
  • Hora (D2) divisional chart: the BPHS Parashari convention (odd sign first half -> Leo / Sun's hora, second half -> Cancer / Moon's hora; even sign reversed). varga(lon, 2); vargas-golden oracle + cited entries. Completes the deferred varga set; alternate hora schemes remain a possible later variant.
  • Kemadruma yoga: the Moon isolated -- no graha in the 2nd or 12th from, or with, the Moon. kemadruma (pure) and kemadrumaAt (from a chart), with the planet set parameterized (includeSun/includeNodes; default the five tara grahas) since the texts vary. yogas-golden pin + a present/absent and toggle oracle, cited in validate_jyotish. Completes the deferred-plan Bucket A.
  • Ashtottari dasha (deferred-plan Bucket B): the 108-year eight-lord conditional dasha (Sun 6 .. Venus 21), with the irregular nakshatra-to-lord groups and the across-span balance reproduced from the JHora/PVR Narasimha Rao convention -- the one the texts vary around, now pinned to that named source rather than guessed. ashtottariDashas/ashtottariActive/ashtottariAt/ashtottariLord. Python reference + ashtottari-golden pin (108-year-total, tiling, and mapping invariants) + cited validate_jyotish checks.
  • Lordship + graha-drishti layer and the raja/dhana yogas (deferred-plan Bucket B, the large build): house lordship (houseLord/signLord/houseSign), Vedic aspects (aspectsSign — every planet the 7th, Mars 4/8, Jupiter 5/9, Saturn 3/10), and association primitives (associationType/parivartana: conjunction / mutual aspect / exchange). On top: rajaYogas (kendra lord associated with a trikona lord), dhanaYogas (two wealth-house 2/5/9/11 lords), and yogakarakas (a planet ruling both a pure kendra and trikona), with rajaYogasAt/dhanaYogasAt. The foundation unlocks a class of future yogas. rajayoga-golden pin + drishti/yogakaraka/raja oracles, cited in validate_jyotish (BPHS).
  • Inter-planetary primary directions (deferred-plan, the last item): the Placidus semi-arc mundane direction of one planet to another, arc = MD_p - (MD_s / SA_s) * SA_p (meridian distance over semi-arc, with the diurnal/nocturnal branch). mundaneDirectionArc and mundaneDirections (all promissor->significator pairs within a span, by time key). Extends directions-golden; validated by tying it to the already-validated angle directions -- it reduces to 0 for a self-direction and to the to-MC arc for an above-horizon promissor directed to a significator on the meridian.

Validation

  • validate_jyotish tier (python/validate_jyotish.py + jyotish-reference.json): pins the Vedic technique conventions to named authorities (BPHS; PyJHora/PVR Rao for variant cases) by replaying a committed, per-check-cited reference set, the way positions are pinned to Swiss Ephemeris and JPL Horizons. Runs no external tool (stays swisseph-free); grows as deferred techniques land. Documented in ARCHITECTURE.md.

MCP server (caelus-mcp)

  • Phase 2 Vedic harvest — four new tools take the surface from eighteen to twenty-two, all defaulting to the sidereal Lahiri zodiac:
    • nakshatras — the nakshatra (lunar mansion), pada, and ruling planet of each classical planet and the Ascendant (lagna).
    • dasha — Vedic dasha periods from the Moon's nakshatra, with a system selector for Vimshottari (120-year), Yogini (36-year), or Ashtottari (108-year): the maha → antar timeline and the lords active at a target date (Vimshottari also gives the pratyantardasha).
    • vargas — the Parashari divisional charts (D1/D2/D3/D9/D10/D12/D30): the divisional sign of each planet and the Ascendant.
    • yogas — Vedic yogas on the rasi chart: the five Pancha Mahapurusha yogas, Gajakesari, Budha-Aditya, Chandra-Mangala, Kemadruma, plus the raja/dhana yogas and the chart's yogakarakas.
  • directions gains an include_mundane option that adds the inter-planetary (promissor → significator) directions alongside the directions to the angles.
  • Each new tool gains verify_tools engine-oracle checks and a frozen golden-mcp payload; self-check eval fixtures cover tool selection and argument shape for all of them.
  • Chart widget (MCP Apps / Apps SDK): natal_chart and current_sky now bind to a ui://widget/chart.html resource so hosts that support the standard (ChatGPT and others) render the chart wheel in-host. The resource loads a self-contained bundle (apps/web/widget to /embed/chart-widget.js) directly in the host sandbox — no nested frame — and renders caelus-wheel from the tool's structuredContent; the text content is unchanged, so non-UI clients are unaffected. Uses the current MCP Apps metadata keys (loading the script needs only resourceDomains) with the legacy openai/* aliases for compatibility. See docs/mcp-app-wiring.md.

v0.13.0 — hellenistic time-lords + Vedic layer (9→18 MCP tools)

2026-06-14

A feature release across all four packages. The engine completes Phase 1 — the hellenistic time-lords (lots, profections, firdaria, zodiacal releasing) and primary directions to the angles — and lays the Phase 2 Vedic layer (nakshatras, the Vimshottari and Yogini dashas, the Parashari vargas, and the placement-based yogas), each pinned by a cross-language golden. The MCP server grows from nine to eighteen tools, surfacing returns, progressions, composite, dignities, and the five Phase 1 time-lord and direction tools.

Engine (caelus)

  • hellenistic lots (Arabic parts), sect-aware (Roadmap Phase 1): the seven Hermetic lots — Fortune, Spirit, Eros, Necessity, Courage, Victory, Nemesis — via lots(engine, jdUt, lat, lonEast, zodiac) plus the pure formula helpers hermeticLots, lotFortune, lotSpirit. Arithmetic on the validated longitudes; landed in the Python reference first and pinned by a new cross-language golden (lots-golden), which also checks that Fortune and Spirit are symmetric about the Ascendant — an invariant any correct port must satisfy, so a shared formula bug cannot pass through both.
  • Annual and monthly profections (Roadmap Phase 1): profection(ascSign, natalJd, targetJd) and profectionAt(engine, natalJd, targetJd, lat, lonEast, zodiac), plus profectedSign/signRuler. The Ascendant advances one whole sign per year; the profected sign's traditional ruler is the lord of the year. Python reference + profections-golden cross-language pin, with a textbook-fact oracle in the test.
  • Firdaria (Roadmap Phase 1): the Persian/medieval planetary time-lord periods — nine periods totalling 75 years (seven planets in the firdaria order, then the two nodes), each planetary period split into seven sub-periods; day vs night start. firdaria, firdariaSequence, firdariaActive, firdariaAt. Python reference + firdaria-golden cross-language pin, with 75-year-total and sub-period-tiling invariants in the test.
  • Zodiacal releasing / aphesis (Roadmap Phase 1, completing it): the hellenistic time-lord technique from Valens, released from a Lot. zrRelease (the L1..Ln timeline), zrActive (the L1..L4 lords at a moment), and zrAt (releasing from the chart's Lot of Spirit or Fortune). Standard Valens/Schmidt convention: 360-day years, each level a twelfth of the one above, loosing of the bond jumping to the opposite sign. Algorithm pinned to a reference port and the published literature; releasing-golden cross-language pin plus invariants in the test (L1/L2 tiling, the +6 jump, and the ~17.58-year loosing-of-the-bond threshold across all twelve Lot signs).
  • Vedic / Jyotish layer (Roadmap Phase 2): nakshatras and the Vimshottari dasha on the validated sidereal longitudes. nakshatra/nakshatraAt (the 27 lunar mansions, padas, and lords) and vimshottariDashas/vimshottariActive/ vimshottariAt (the 120-year dasha sequence, mahadasha/antardasha/ pratyantardasha, started from the Moon's nakshatra). Lahiri ayanamsa and a 365.25-day dasha year by default. Python reference + vedic-golden pin, with 120-year-total and antardasha-tiling invariants. Floor division uses math.floor in the reference so sign/nakshatra boundaries match JavaScript bit for bit (Python // buckets exact boundaries differently).
  • Vargas / divisional charts (Roadmap Phase 2): the textbook Parashari set — D1 (rasi), D3 (drekkana), D9 (navamsa), D10 (dasamsa), D12 (dwadasamsa). The contested hora (D2) and unequal trimsamsa (D30) are deferred until their conventions are pinned. varga (placement of a longitude), vargaAt (of a body), and vargaChart (the full divisional chart). Computed from rasi + division (exact at the sign boundaries) over the validated sidereal longitudes; vargas-golden pin plus a textbook-placement oracle (navamsa Aries->Aries / Taurus->Capricorn, drekkana +4/+8, dasamsa odd/even).
  • Yogini dasha (Roadmap Phase 2): the 36-year nakshatra-based cycle of eight yoginis (Mangala..Sankata, periods 1..8), started from the Moon's nakshatra by the add-3 rule, with proportional sub-periods. yoginiDashas/yoginiActive/ yoginiAt. Python reference + yogini-golden pin, with 36-year-total, sub-period-tiling, and starting-yogini (Ashwini -> Bhramari) invariants.
  • Vedic yogas / placement combinations (Roadmap Phase 2): the well-defined, placement-based combinations on the sidereal rasi chart — the five Pancha Mahapurusha yogas (Ruchaka, Bhadra, Hamsa, Malavya, Shasha: a non-luminary in its own sign or exaltation and in a kendra), Gajakesari (Jupiter in a kendra from the Moon), Budha-Aditya (Sun + Mercury in one sign), and Chandra-Mangala (Moon + Mars in one sign). detectYogas (pure, from a sign map) and yogasAt (from a chart), reusing the engine's dignities for own-sign/exaltation. The variant-laden yogas (Kemadruma, lordship-based raja/dhana) are deferred. yogas-golden pin plus a defining-rule oracle (in vs. off kendra, kendra-from-Moon, same-sign).
  • Primary directions to the angles (Roadmap Phase 1, completing it): directionArcs (direct arcs of a body to MC/IC/Asc/Desc by the Placidus semi-arc, via the ascensional difference) and primaryDirections (the bodies' directions to the angles within a span, by the Ptolemy or Naibod time key). Computed on the validated equatorial coordinates and RAMC. directions-golden pin plus geometric invariants (IC = MC + 180, the ascensional-difference relationships, circumpolar Asc/Desc, the Naibod key ratio).

MCP server (caelus-mcp)

  • Four new tools surfacing engine capabilities that were already suite-pinned in caelus but not yet exposed over MCP (Roadmap Phase 0):
    • returns — solar/lunar return instants in a window plus the full return chart for the first, cast at a return location (defaults to the birthplace).
    • progressions — secondary progressions (day-for-a-year) and solar-arc directions to a target date; longitudes only, no birthplace needed.
    • composite — midpoint composite (bodies and angles) and the Davison chart.
    • dignities — essential dignity (domicile/exaltation/detriment/fall) and sect for the seven traditional planets at a moment and place.
  • lots (Roadmap Phase 1): the seven Hermetic lots (Arabic parts) — Fortune, Spirit, Eros, Necessity, Courage, Victory, Nemesis — cast from the Ascendant and sect-aware, surfacing the engine's lots().
  • profections (Roadmap Phase 1): annual and monthly profections to a target date — age, the profected signs and their whole-sign houses, and the lord of the year — surfacing profectionAt().
  • firdaria (Roadmap Phase 1): the firdaria planetary time-lord periods — the full 75-year timeline (nine periods, seven sub-periods each) and the lords active at a target date — surfacing firdaria()/firdariaActive().
  • releasing (Roadmap Phase 1): zodiacal releasing (aphesis) from the Lot of Spirit or Fortune — the L1–L4 period timeline (with loosing of the bond) and the lords active at a target date — surfacing zrRelease()/zrActive().
  • directions (Roadmap Phase 1): primary directions of the seven traditional planets to the four angles by the Naibod or Ptolemy time key, sorted by age — surfacing primaryDirections(). Completes the Phase 1 surface over MCP.
  • No engine change in this layer. Each tool gains engine-oracle checks in verify_tools.mjs (the lots checks include the Fortune/Spirit symmetry invariant; firdaria the 75-year-total and sub-period-tiling invariants; releasing the +6 loosing-of-the-bond and L2-tiling invariants; directions the IC = MC + 180 and time-key invariants) and frozen payloads in golden-mcp.json; the tool surface is now eighteen.

v0.12.1 — caelus-mcp on the official MCP Registry

2026-06-14

A caelus-mcp metadata patch: registry listing only, no functional change. The other three packages stay at 0.12.0.

MCP server (caelus-mcp)

  • Listed on the official MCP Registry as io.github.heavyblotto/caelus-mcp. Adds an mcpName field to package.json and a server.json describing the npm package (stdio) and the hosted Streamable HTTP endpoint, so the server is discoverable from the Registry and the directories that sync from it. The README gains a one-line claude mcp add install.

v0.12.0 — chartAt + filled-out API reference

2026-06-14

A JD-first chart entry point. No breaking changes; the position conformance suite is unchanged at 3,218 checks.

Engine (caelus)

  • Engine.chartAt(jdUt, lat, lonEast, opts): build a full chart directly from a Julian Day (UT), with no calendar round-trip. engine.chart() now converts its calendar fields to a JD and delegates to chartAt, so the two share one code path and return identical results. The natural entry point for callers that already hold a JD — transit/event scans, rankMoments winners, and position/longitude workflows — and it sidesteps the common chart(jd, …) misuse that throws RangeError: jd … outside fitted range. Mirrored in the Python reference (chart_at) and guarded by a chartAt == chart equivalence assertion in the golden suite.

Docs & reference

  • /docs/charts presents chartAt as the first-class path for charting from a Julian Day and clarifies that chart() takes calendar fields, not a JD; the electional mini-app builds the winner's chart with chartAt(best.jd, …) instead of a manual JD-to-calendar conversion.
  • API reference filled out: every recommended- and advanced-tier symbol now carries full doc comments — parameter descriptions, return shapes, thrown errors, runnable examples, and cross-references — and the Chart, ChartOptions, Position, and related interfaces document every field (units, ranges, null cases). The same text surfaces on editor hover.
  • Easier to find: Engine methods (chart, chartAt, position, longitude, and the rest) are now individually searchable and deep-linkable (/docs/api/Class.Engine#chartat), the /docs/api index surfaces the Engine method set directly, and every generated heading is anchored.

v0.11.0 — chart feature space + geometric compiler

2026-06-14

Two engine layers that treat a chart as something to match and to synthesize. No breaking changes to the 0.10.x surface; the position conformance suite is unchanged at 3,218 checks, and two new cross-language goldens pin the additions to the Python reference.

Engine (caelus)

  • Chart feature space: chartFeatures maps the sky at an instant to a vector (each body's longitude as a weighted unit-circle point), cosineSimilarity and configurationFit measure how alike two configurations are, and searchConfigurations ranks a time range by resemblance to a target form. The deterministic substrate for matching, retrieving, and searching chart configurations. Reference-first, pinned by test/features-golden.json.
  • Geometric compiler: compileForm inverts (time, place) -> chart. Given weighted geometric constraints (aspect, sign, degree), it finds the body longitudes that best satisfy them via deterministic coordinate descent, reports the residual and worst constraint, and flags a form as impossible when even the best fit is poor. constraintLoss and formLoss are the pure loss functions. Reference-first, pinned by test/compiler-golden.json.

v0.10.0 — 3D sphere, astrocartography, graphic ephemeris

2026-06-14

A visualization tranche: 3D chart spheres, astrocartography, and a graphic ephemeris, each landing engine math plus an SSR-safe render. No breaking changes to the 0.9.x surface; the position conformance suite is unchanged at 3,218 checks, and three new cross-language goldens pin the additions.

Engine (caelus)

  • Spherical geometry: angularSeparation3d and unitVector, the true great-circle angle between two bodies from their ecliptic longitude and latitude. This is the 3D aspect, wider or narrower than the 2D longitude difference by the bodies' latitude. Reference-first, pinned by test/spherical-golden.json.
  • Astrocartography: astrocartography and planetLines give where each body sits on the four angles across the globe, the MC/IC meridians and the curved ASC/DSC rising and setting tracks, from RA/Dec and sidereal time. Reference-first, pinned by test/astrocartography-golden.json.
  • ephemeris: a time series of one value per body (longitude, latitude, declination, right ascension, or speed) over a range, the data behind a graphic ephemeris. A collector over the already-pinned positions.

Chart wheel (caelus-wheel)

  • ChartSphere: the chart as a tilted celestial sphere, planets at their true ecliptic latitude with the ecliptic and equator drawn as great-circle rings.
  • AstroMap: the astrocartography angle lines on an equirectangular world map, with a graticule basemap and room for your own coastlines as children.
  • EphemerisGraph: the ephemeris series as line graphs, with longitude wraps split. All SSR-safe SVG with no runtime dependencies.

v0.9.0 — electional primitives + hosted MCP

2026-06-14

Electional building blocks and long-scan ergonomics on the engine, the hosted MCP transport, and a self-contained build. No breaking changes to the 0.8.x surface; the position conformance suite is unchanged at 3,218 checks, and two new cross-language goldens pin the additions to the Python reference.

Engine (caelus)

  • Electional primitives: applying and separating aspects, solar phase (cazimi, combust, under the beams), planetary hours, void-of-course Moon, and house placement with angularity. Reference-first, pinned bit-for-bit by test/electional-golden.json (21 specs, 53 checks).
  • scan, rankMoments, and rankMomentsAsync: a batched scan with progress and a top-N moment ranker over a user-supplied score, synchronous or non-blocking. A TS-side layer over the validated primitives, with a deterministic unit suite (14 checks).

MCP server (caelus-mcp)

  • Hosted over MCP Streamable HTTP at https://www.ephemengine.com/api/mcp, stateless, alongside the stdio transport. buildServer(engine?) takes an injectable engine so the same tool surface backs both.
  • Two electional tools (seven to nine): planetary_hours (the hour in effect, its ruler and day/night span, the day ruler, and the 24-hour Chaldean sequence) and void_of_course (the Moon's sign, sign-exit time, and next perfecting aspect to Sun..Saturn).
  • natal_chart and current_sky now tag each body with its solar phase (cazimi, combust, under the beams) and each aspect as applying or separating. Additive and optional, so a payload still feeds <ChartWheel> unchanged.
  • caelus://glossary gains an electional block (solar-phase thresholds, Chaldean and day rulers, the void-of-course and aspect-phase definitions).

Tooling and docs

  • npm run build now generates the API reference and the search index, so a clean build produces a fully crawlable site.
  • A cross-package integration test covers the local time to chart to wheel journey end to end.
  • npm run bundle-sizes reports per-entrypoint sizes with esbuild; the data-tiers page gains a bundle-tradeoffs section.
  • New site pages: methods, features, and how this was built.
  • Corrected the sidereal ayanamsa count in stray docs (seven, not eight).

v0.8.0 — turbo tier + MCP resources/prompts

2026-06-13

A turbo evaluation tier and the phase-2 MCP surface. No breaking changes to the 0.7.x surface; the position conformance suite is unchanged at 3,218 checks.

Engine (caelus)

  • Turbo tier (Turbo): a segmented Chebyshev representation of the engine's apparent longitude, fit to the engine itself, so a longitude costs a couple of dozen multiply-adds. About 580x faster than the full engine, reproducing it to under 0.01" for the planets and ~0.03" for the Moon. The pack is a mint-it-for-your-range artifact; fit_turbo.py mints one with a pure-Python fit (no numpy). The TS evaluator is bit-identical to the Python reference, pinned by test/turbo-golden.json (110 cases, worst diff 0).

MCP server (caelus-mcp)

  • Resources: caelus://glossary (aspect angles and default orbs, signs, bodies, the twelve house systems, essential dignities) and caelus://accuracy (the validation table vs Swiss Ephemeris and JPL Horizons).
  • Prompt: rectification_session, a multi-turn script around rectification_grid and find_aspect_dates.

v0.7.0 — derived-charts layer

2026-06-13

A derived-charts layer: standard astrological derivations computed on the validated primitives. No breaking changes to the 0.6.x surface; the position conformance suite is unchanged at 3,218 checks, and a new cross-language golden (52 checks) pins the TypeScript port to the Python reference, bit-identical.

Engine (caelus)

  • Returns (returns, solarReturn, lunarReturn): the crossing search against a natal longitude.
  • Secondary progressions (progressedJd, progressedLongitude): the day-for-a-year mapping. Solar arc (solarArc, directedLongitude): the true progressed-Sun arc, applied forward.
  • Composite (compositeLongitudes): shorter-arc midpoints. Davison (davisonParams): the midpoint in time and place.
  • Harmonics (harmonicLongitude, harmonicChart); antiscia (antiscion, contraAntiscion); declination aspects (declinationAspect, declinationAspects); out-of-bounds (outOfBounds, outOfBoundsMargin).
  • Dignities (dignities, dignityOf): domicile, exaltation, detriment, fall. Sect (isDayChart, planetarySect, inSect): day-night by Sun altitude.
  • All exported from the package root and mirrored between the TS engine and the Python reference (astroengine/derived.py), pinned by test/derived-golden.json.

Docs and tooling

  • Community-health files: CONTRIBUTING.md, CODE_OF_CONDUCT.md, SECURITY.md.
  • The caelus-starter template moved to its own repository.

v0.6.0 — the when() query language

2026-06-13

A declarative query language: the engine answers "where is the body?", and when() answers "when is the configuration true?" over a time range. No breaking changes to the 0.5.x surface; the position conformance suite is unchanged at 3,218 checks, and a new cross-language golden (38 boundary checks) pins the TypeScript port to the Python reference, boundary diff 0 s.

Engine (caelus)

  • Query language (when()): a predicate is a continuous margin function, true exactly where margin >= 0. Logical combinations reduce to the same form (allOf = min, anyOf = max, notOf = negation), so any query is one continuous function solved with the same coarse-scan-then-bisect root finder as events.crossings. Predicates ship for aspect (orb around any of seven exact angles, to a body or a fixed longitude), inSign, and retrograde / notRetrograde; all accept a zodiac mode. when() returns the intervals where the predicate holds, auto-selecting a 0.125 d scan step when a fast body (Moon, nodes, Lilith) is involved and 1 d otherwise. Exported from the package root.
  • The TypeScript port mirrors the Python reference (astroengine/query.py); the two are pinned by test/query-golden.json (interval boundaries agree to 0 s).

Docs and tooling

  • ARCHITECTURE.md rewritten as an actual architecture document.
  • ROADMAP.md added: durable, public-safe project plan.
  • templates/starter README rewritten in the project's voice.
  • Removed unused DE441 Moon refit tooling (fit_moon.py, horizons.py).

v0.5.0 — fixed stars, eclipses, Gauquelin sectors

2026-06-13

Swiss Ephemeris gap analysis Tiers 2 and 3 close (see docs/gap-analysis.md): every line item from the original plan is now shipped or explicitly documented as out of scope. No breaking changes to the 0.4.x surface; the conformance suite grew from 3,177 to 3,218 checks.

Engine (caelus)

  • Fixed stars: 318-star HYG-derived catalog (ICRS J2000 + proper motions, full 3D space motion; CC BY-SA 4.0, attributed in the pack). engine.fixedStar(name, jd, opts?) and starNames(); ≤0.6″ vs swe_fixstar fed the same catalog rows.
  • Star-anchored ayanamsas galcent_0sag and true_citra (the v0.3 deferral closes): the Galactic Center / Spica sits at the fixed sidereal longitude by definition; sidereal Sun ≤0.19″ vs Swiss Ephemeris. Eight zodiac modes total.
  • Gauquelin sectors (gauquelinSector): rise/set of disc center with refraction (SE method 3), exact to the rise/set bound. riseSet gains a discCenter option.
  • Solar and lunar eclipse search (solarEclipses/lunarEclipses), global circumstances: type, gamma, magnitudes, contacts. Types match Swiss Ephemeris exactly over 1990–2030 (92 lunar + 89 solar, none missed, none phantom); maxima ≤9 s; lunar magnitudes ≤0.0013 via Danjon's parallax enlargement (86/85 on the flattened Earth — recovered empirically). Ground paths / local circumstances are the one documented remainder.

MCP server (caelus-mcp)

  • sky_events gains solar_eclipse and lunar_eclipse kinds — the reserved Tier 3 extension.
  • The zodiac parameter grows to eight modes (star-anchored ayanamsas).

v0.4.0 — event search + new bodies

2026-06-13

Swiss Ephemeris gap analysis Tier 2, minus fixed stars (see docs/gap-analysis.md), plus deployment-boundary fixes from an external review. No breaking changes to the 0.3.x surface; the conformance suite grew from 3,087 to 3,177 checks; the engine computes 28 bodies.

Engine (caelus)

  • Event search (events module): rise/set/meridian transits (≤0.5 s vs swe_rise_trans, polar no-event cases agree), zodiac degree crossings (≤4 s), lunar phases (≤4 s), retrograde stations (~1 minute — ill-conditioned by nature).
  • New bodies, on request via ChartOptions.bodies or position(): true_lilith (osculating apogee; hypersensitive to the lunar theory — see accuracy.json for the SE-oracle caveat), the big-four asteroids + Pholus (ceres, pallas, juno, vesta, pholus; JPL Horizons Chebyshev fits 1850–2150, ≤1″ geocentric, Node/lazy data tier), and the eight Hamburg-school Uranian bodies (cupido…poseidon; constant- element Kepler pack calibrated to Swiss Ephemeris 2.10, ≤2.3″).
  • loadNodeData falls back per planet to the embedded VSOP tier against the published tarball instead of throwing.

MCP server (caelus-mcp)

  • sky_events — the seventh outcome-level tool: event search in a date range (≤370 days) for rise/set/meridian transits, lunar phases, stations, and zodiac crossings. Eclipses will extend it, not add a tool.

Corrections and deployment

  • True-node accuracy claim corrected on every surface: ≤1′ vs SE's built-in ephemeris (≤1″ only vs full JPL DE431); now pinned by the claims linter.
  • Live-deploy smoke test (live-smoke workflow) guards the production API on every push to main, daily, and on dispatch.

v0.3.0 — sidereal zodiac, eight house systems, topocentric

2026-06-12

Swiss Ephemeris gap analysis Tier 1 (see docs/gap-analysis.md). No breaking changes to the 0.2.x surface; the conformance suite grew from 1,438 to 3,087 checks, and every new feature is measured against Swiss Ephemeris 2.10 by the new python/validate_swiss.py harness.

Engine (caelus)

  • Sidereal zodiac: zodiac: "sidereal:<ayanamsa>" with five fixed-epoch ayanamsas (lahiri, fagan_bradley, krishnamurti, raman, yukteshwar). Sidereal longitudes agree with Swiss Ephemeris to 0.08″ (≤0.30″ at the range edges, from the precession-model difference).
  • Eight new house systems, all exact against swe_houses_armc over 200 polar-inclusive cases each: Koch, Regiomontanus, Campanus, Alcabitius, Morinus, Meridian, Polich-Page, Vehlow. Twelve systems total.
  • Position gains lat (ecliptic latitude), dist (AU for every body, Moon included), ra, dec (true equinox of date).
  • Topocentric positions (topocentric: true + observer), geometric heliocentric() query, mean Lilith available on request (≤1.3″), vertex and east point on Chart.angles.
  • pheno(): phase angle, illuminated fraction, elongation, apparent diameter, and apparent magnitude (Mallama & Hilton 2018, with the Saturn ring term and Neptune's secular ramp; Moon via Allen's phase law, valid to phase angle ~140°). Plus equationOfTime(), azAlt(), and Saemundsson/Bennett refraction.
  • Options-object API per docs/api-v0.3.md: position(body, jdUt, opts) and chart(…, opts); chart()'s ninth argument still accepts the 0.2.x house-system string. BodyId accepts any string id; engine.bodies() reports what the loaded data can compute.
  • Bug fix: the ascendant at polar latitudes (|lat| > ~66°) could be the setting intersection, 180° off. The ASC now always lies in (MC, MC+180°), matching Swiss Ephemeris. This changes whole-sign fallback charts above the polar circles.

MCP server (caelus-mcp)

  • zodiac parameter on natal_chart, current_sky, transits, synastry, and find_aspect_dates; house_system widened to the twelve systems. Defaults leave existing payloads byte-identical.
  • Payloads carry a zodiac key only when sidereal.

v0.2.1 — README-only npm patch

2026-06-12

  • README-only patch so the npm package pages render the docs.

v0.2.0 — structured aspect objects across MCP

2026-06-12

  • Structured aspect objects across the MCP surface ({"a","b","aspect","orb"}, transits add t/n and applying); chart payloads feed caelus-wheel's <ChartWheel> with no adapter.
  • The MCP handshake reports the real package version.

v0.1.1 — fix caelus-mcp npx exit

2026-06-12

  • Fix caelus-mcp silently exiting when launched via npx.

v0.1.0 — first release of all four packages

2026-06-12

First release of all four packages, published with npm provenance.

  • caelus: MIT, written from published sources (VSOP87D, Meeus, IAU 1980, JPL DE423/Horizons fits) — no Swiss Ephemeris code, no AGPL, no ephemeris files. Sun–Pluto, Chiron, both lunar nodes; speeds and retrogrades; ASC/MC; Placidus/Porphyry/Equal/Whole Sign houses with an explicit polar fallback; major aspects. Apparent geocentric positions, 1800–2149. Per-body accuracy vs Swiss Ephemeris 2.10 (1900–2099): Sun–Saturn ≤1″, Uranus ≤1.9″, Neptune ≤4.6″, Moon ≤2.5″ (precise tier), Pluto ≤2.5″, Chiron ≤1″, mean node ≤1″; true node ≤ 1′ vs SE's built-in ephemeris (corrected 2026-06-12 — originally misstated as ≤1″; the ≤1″ figure holds only vs full JPL DE431). TypeScript port pinned to the Python reference by 1,438 golden checks (worst deviation 0.82 nano-arcseconds at release).
  • caelus-mcp: six outcome-level tools over stdio (natal_chart, current_sky, transits, synastry, find_aspect_dates, rectification_grid); ~2 KB natal payloads.
  • caelus-birth: local birth time + place → UT, with DST edge cases reported (ambiguous/nonexistent).
  • caelus-wheel: React SVG chart wheel, zero runtime dependencies.

Install the latest

Quickstart →