Initial Commit

This commit is contained in:
2026-05-27 23:29:53 +01:00
commit fbc70f96e6
10000 changed files with 1102152 additions and 0 deletions

View File

@@ -0,0 +1,110 @@
## ADDED Requirements
### Requirement: SolarProvider implementation
The system SHALL export `createSolarSystemProvider` returning a `SolarProvider` that computes real solar system body positions.
#### Scenario: Sun altitude at noon
- **WHEN** `getBody("Sun", observer, time)` is called for an observer at latitude `0` at local noon
- **THEN** the returned `altitude` is approximately `90` minus the absolute declination offset
### Requirement: Astronomy.js engine injection
The system SHALL accept an injectable `AstronomyEngine` in `createSolarSystemProvider`, defaulting to astronomy.js.
#### Scenario: Deterministic engine injection
- **WHEN** a deterministic mock `AstronomyEngine` is injected
- **THEN** `getBodies` returns exactly the mocked positions
### Requirement: Keplerian propagator for custom planets
The system SHALL propagate positions for planets with `OrbitalConfig` using a Keplerian solver from epoch.
#### Scenario: Custom planet position
- **WHEN** a `PlanetConfig` with valid `OrbitalConfig` is used as observer's planet or target body
- **THEN** `getBodies` includes the custom planet with a propagated heliocentric position
### Requirement: Angular diameter computation
The system SHALL compute `angularDiameterArcmin` as `2 * arctan(radius / distance) * (180/π * 60)`.
#### Scenario: Sun angular diameter
- **WHEN** `getBody("Sun", ...)` is called
- **THEN** `angularDiameterArcmin` is approximately `32` arcminutes
### Requirement: Apparent magnitude for real bodies
The system SHALL compute `apparentMagnitude` for real bodies using phase angle and distance via astronomy.js.
#### Scenario: Venus magnitude range
- **WHEN** `getBody("Venus", ...)` is called at multiple times
- **THEN** `apparentMagnitude` varies between approximately `-4.9` and `-3.8`
### Requirement: Sunrise and sunset computation
The system SHALL compute sunrise and sunset dates in UTC for a given observer and calendar date.
#### Scenario: Equator sunrise consistency
- **WHEN** `getSunrise` and `getSunset` are called for an equatorial observer on an equinox date
- **THEN** sunrise is approximately 12 hours before sunset
### Requirement: Season computation
The system SHALL export `getSeason` defaulting to Earth but accepting any `PlanetConfig` with `axialTilt` and `OrbitalConfig`.
#### Scenario: Northern hemisphere season
- **WHEN** `getSeason(new Date("2026-06-21"), EARTH)` is called
- **THEN** the result is `summer`
### Requirement: Equinox and solstice prediction
The system SHALL export `getNextEquinox` and `getNextSolstice` for any configured planet.
#### Scenario: Next equinox after a date
- **WHEN** `getNextEquinox(new Date("2026-01-01"), EARTH)` is called
- **THEN** the result is a `Date` in March 2026
### Requirement: Lunar phase
The system SHALL export `getLunarPhase` returning phase (0–1), illumination percentage, and name for Earth/Moon.
#### Scenario: Full moon phase
- **WHEN** `getLunarPhase(fullMoonDate)` is called
- **THEN** `phase` is approximately `0.5`
- **AND** `illumination` is approximately `100%`
### Requirement: Eclipse prediction
The system SHALL export `predictEclipse` for solar and lunar eclipses on Earth.
#### Scenario: Known eclipse
- **WHEN** `predictEclipse(new Date("2026-01-01"), "solar")` is called
- **THEN** the returned `EclipseEvent` has a date after the input and a `totality` value
### Requirement: Constellation lookup
The system SHALL export `getConstellation` mapping RA/Dec to IAU constellation name.
#### Scenario: Orion lookup
- **WHEN** `getConstellation(raOrion, decOrion)` is called with Orion's centre coordinates
- **THEN** the result equals `"Orion"`
### Requirement: Atmosphere extinction for surface observers
The system SHALL apply atmospheric extinction to apparent magnitudes when the observer has an atmosphere.
#### Scenario: Horizon extinction
- **WHEN** `getBody("Sun", surfaceObserver, time)` is called with the Sun near the horizon
- **THEN** `apparentMagnitude` is dimmer than the vacuum value