rust_zmanim/lib.rs
1// This library is free software; you can redistribute it and/or
2// modify it under the terms of the GNU Lesser General Public
3// License as published by the Free Software Foundation; either
4// version 2.1 of the License, or (at your option) any later version.
5//
6// This library is distributed in the hope that it will be useful,
7// but WITHOUT ANY WARRANTY; without even the implied warranty of
8// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
9// Lesser General Public License for more details.
10//
11// You should have received a copy of the GNU Lesser General Public
12// License along with this library; if not, see:
13// <https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html>
14
15//! # rust-zmanim
16//! Calculate different astronomical times including sunrise and sunset and
17//! Jewish *zmanim* or religious times for prayers and other Jewish religious
18//! duties.
19//!
20//! The [`astronomical_calculator`] provides non-religious astronomical / solar
21//! calculations such as sunrise, sunset and twilight.
22//!
23//! The [`zmanim_calculator`] contains the basics for *zmanim* calculations.
24//!
25//! The [`complex_zmanim_calendar`] provides a stateful struct with many premade
26//! *zmanim* calculations, both built on the [`zmanim_calculator`] API.
27//!
28//! This project is a port from pinnymz's [python-zmanim
29//! project](https://github.com/pinnymz/python-zmanim) and Eliyahu Hershfeld's
30//! [KosherJava project](https://github.com/KosherJava/zmanim). Much of the code
31//! is ported directly from `python-zmanim` and `KosherJava`, and almost all of
32//! the documentation is from `KosherJava`
33//!
34//! See the [KosherJava site](https://kosherjava.com) for additional information
35//! on the original Java project and *zmanim* in general.
36//!
37//! **Note:** It is important to read the technical notes on top of the
38//! [`astronomical_calculator`] documentation.
39//!
40//! ### Disclaimer
41//! I did my best to get accurate results using standardized astronomical
42//! calculations. Please use care when using the library for *halacha lemaaseh*
43//! applications. **Also**, despite the great *precision* of the returned
44//! values, the *accuracy* is nowhere near that. To quote the NOAA, whose
45//! algorithm this crate uses, "due to variations in atmospheric composition,
46//! temperature, pressure and conditions, observed values may vary from
47//! calculations"
48//!
49//! ## Example (more examples in /examples)
50//! ```rust
51//! use jiff::{civil, tz::TimeZone};
52//! use rust_zmanim::prelude::*;
53//!
54//! let date = civil::date(2025, 7, 29);
55//!
56//! // your location here
57//! let beit_meir = GeoLocation {
58//! latitude: 31.7975,
59//! longitude: 35.0345,
60//! elevation: 526.0,
61//! timezone: TimeZone::get("Asia/Jerusalem").unwrap(),
62//! };
63//!
64//! // the zmanim_calculator provides some basic building blocks of zmanim
65//! if let Some(sunrise) = zmanim_calculator::hanetz(&date, &beit_meir, false) {
66//! assert_eq!(
67//! sunrise.strftime("%Y-%m-%d %H:%M:%S.%f %Z").to_string(),
68//! "2025-07-29 05:53:39.574572512 IDT"
69//! );
70//! }
71//!
72//! // zmanim_calculator also lets you make any custom tzeis, alos, etc using
73//! // ZmanOffset. these may be based on degrees, fixed time, or shaos zmaniyos
74//! if let Some(tzeis_degrees) =
75//! zmanim_calculator::tzeis(&date, &beit_meir, false, &ZmanOffset::Degrees(6.13))
76//! {
77//! assert_eq!(
78//! tzeis_degrees
79//! .strftime("%Y-%m-%d %H:%M:%S.%f %Z")
80//! .to_string(),
81//! "2025-07-29 20:06:02.501735285 IDT"
82//! );
83//! }
84//!
85//! // there is also a ComplexZmanimCalendar struct which stores the date and
86//! // location, convenient for getting many zmanim for the same point in 4D space.
87//! // It also has many common zmanim pre-made
88//! let czc = ComplexZmanimCalendar {
89//! geo_location: beit_meir,
90//! date,
91//! use_elevation: UseElevation::No,
92//! };
93//!
94//! if let Some(alos120) = czc.alos_120_minutes() {
95//! assert_eq!(
96//! alos120.strftime("%Y-%m-%d %H:%M:%S.%f %Z").to_string(),
97//! "2025-07-29 03:53:39.574572512 IDT"
98//! );
99//! }
100//!
101//! if let Some(sz18) = czc.shaah_zmanis_mga_18_degrees() {
102//! // 01:24:14.106060472
103//! assert_eq!(sz18.as_nanos(), 5_054_106_060_472);
104//! }
105//!
106//! // the calculations will return None if the specified solar event will not
107//! // occur
108//! let north_pole = GeoLocation {
109//! latitude: 90.0,
110//! longitude: 0.0,
111//! elevation: 0.0,
112//! timezone: TimeZone::UTC,
113//! };
114//! let polar_sunset = zmanim_calculator::shkia(&date, &north_pole, false);
115//! assert!(polar_sunset.is_none());
116//! ```
117
118pub mod astronomical_calculator;
119pub mod complex_zmanim_calendar;
120pub mod util;
121pub mod zmanim_calculator;
122
123/// A convenience module for glob imports. `use rust_zmanim::prelude::*;`
124pub mod prelude {
125 pub use crate::astronomical_calculator;
126 pub use crate::zmanim_calculator;
127
128 pub use crate::complex_zmanim_calendar::*;
129 pub use crate::util::geolocation::GeoLocation;
130 pub use zmanim_calculator::ZmanOffset;
131}