# noaa-go

[![CI](https://github.com/hebcal/noaa-go/actions/workflows/ci.yml/badge.svg)](https://github.com/hebcal/noaa-go/actions/workflows/ci.yml)
[![Go Reference](https://pkg.go.dev/badge/github.com/hebcal/noaa-go.svg)](https://pkg.go.dev/github.com/hebcal/noaa-go)

Package `noaa` calculates astronomical solar positions — sunrise, sunset, solar
noon and midnight, solar elevation and azimuth, the equation of time, and more.

It is a Go port of the solar-position calculators from the
[KosherJava Zmanim API](https://github.com/KosherJava/zmanim) by Eliyahu
Hershfeld. The port focuses **exclusively on solar-position math** and
deliberately omits the halachic (zmanim) calendar layers of the original
library.

Two algorithms are provided, both implementing the `Calculator` interface:

- **`NOAACalculator`** — the widely used
  [National Oceanic and Atmospheric Administration](https://gml.noaa.gov/grad/solcalc/)
  algorithm, itself based on the low-accuracy solar-position method from Jean
  Meeus's *Astronomical Algorithms* (good to roughly 0.01° / about 1 minute of
  time).
- **`MeeusCalculator`** — the higher-accuracy method from the same work,
  computing the Earth's heliocentric position from the abridged VSOP87 series
  (good to roughly an arc-second). It also applies a ΔT (TT − UT) correction
  that `NOAACalculator` omits.

## Install

```sh
go get github.com/hebcal/noaa-go
```

## Usage

```go
package main

import (
	"fmt"
	"time"

	noaa "github.com/hebcal/noaa-go"
)

func main() {
	tz, _ := time.LoadLocation("America/New_York")
	geo, err := noaa.NewGeoLocation("Lakewood, NJ", 40.09789, -74.21764, 0, tz)
	if err != nil {
		panic(err)
	}

	calc := noaa.NewNOAACalculator()
	date := time.Date(2025, time.June, 21, 0, 0, 0, 0, time.UTC)

	// UTC times are returned in 24-hour decimal format (5.75 == 05:45:00).
	sunrise := calc.GetUTCSunrise(date, geo, noaa.GeometricZenith, true)
	sunset := calc.GetUTCSunset(date, geo, noaa.GeometricZenith, true)
	noon := calc.GetUTCNoon(date, geo)

	fmt.Printf("sunrise %.4f  noon %.4f  sunset %.4f UTC\n", sunrise, noon, sunset)

	// Solar elevation and azimuth at a specific instant.
	instant := time.Date(2025, time.June, 21, 16, 0, 0, 0, time.UTC)
	fmt.Printf("elevation %.2f°  azimuth %.2f°\n",
		calc.GetSolarElevation(instant, geo),
		calc.GetSolarAzimuth(instant, geo))
}
```

### Zeniths

Rise/set methods take a *zenith* — the angle of the sun below the vertical.
Pass `noaa.GeometricZenith` (90°) for true sunrise/sunset (which is then
automatically adjusted for atmospheric refraction, the sun's radius, and
optionally elevation). For twilight and depression-angle times, pass the
appropriate zenith directly, for example `96.0` for civil twilight (6° below the
horizon) or `108.0` for astronomical twilight (18° below the horizon). No
refraction or radius adjustment is applied for non-90° zeniths.

### Configuration

`NOAACalculator` and `MeeusCalculator` share the configuration accessors of the
underlying astronomical calculator:

- `GetRefraction` / `SetRefraction` — the atmospheric refraction (default 34′).
- `GetSolarRadius` / `SetSolarRadius` — a fixed solar radius (default 16′).
- `IsUseApparentSolarRadius` / `SetUseApparentSolarRadius` — whether to use the
  date-based apparent solar radius (the default) instead of the fixed value.
- `GetEarthRadius` / `SetEarthRadius` — the earth radius used for the elevation
  adjustment.
- `MeeusCalculator.SetApplyDeltaT` — toggle the ΔT correction.

The individual solar-position primitives (declination, equation of time, mean
and true longitude, obliquity, nutation, VSOP-derived apparent ecliptic
coordinates, right ascension, ΔT, and so on) are also exported as methods on the
calculators. See the [package documentation](https://pkg.go.dev/github.com/hebcal/noaa-go)
for the full API.

## Testing

The test suite validates every exported solar function against **golden
reference values generated by running the original KosherJava Java code**
(under Java 21). The Go results match the Java `double` output to within roughly
a microsecond, confirming the port is faithful to the source.

```sh
go test ./...
```

## License

Like the KosherJava code it is derived from, this library is licensed under the
[GNU Lesser General Public License, version 2.1](LICENSE).

- Original Java Zmanim API © 2004–2026 Eliyahu Hershfeld.
- Go port © 2026 Michael J. Radwin.
