diff --git a/Cargo.lock b/Cargo.lock index 3458ffee..de9b0576 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -365,6 +365,7 @@ dependencies = [ "rustc-hash", "tinystr", "tzif", + "web-time", ] [[package]] @@ -447,6 +448,16 @@ version = "0.2.95" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "65fc09f10666a9f147042251e0dda9c18f166ff7de300607007e96bdebc1068d" +[[package]] +name = "web-time" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a6580f308b1fad9207618087a65c04e7a10bc77e02c8e84e9b00dd4b12fa0bb" +dependencies = [ + "js-sys", + "wasm-bindgen", +] + [[package]] name = "windows-core" version = "0.52.0" diff --git a/Cargo.toml b/Cargo.toml index f4f8b62b..7f48f884 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -34,6 +34,9 @@ tzif = { version = "0.2.3", optional = true } jiff-tzdb = { version = "0.1.1", optional = true } combine = { version = "4.6.7", optional = true } +# System time feature +web-time = { version = "1.1.0", optional = true } + [features] log = ["dep:log"] experimental = ["tzdb"] diff --git a/src/components/now.rs b/src/components/now.rs index e35689d5..9d513faf 100644 --- a/src/components/now.rs +++ b/src/components/now.rs @@ -35,7 +35,7 @@ impl Now { pub fn plain_date_time_with_provider( tz: Option, - provider: &mut impl TzProvider, + provider: &impl TzProvider, ) -> TemporalResult { let iso = system_date_time(tz, provider)?; Ok(PlainDateTime::new_unchecked(iso, Calendar::default())) @@ -45,7 +45,7 @@ impl Now { #[cfg(feature = "std")] fn system_date_time( tz: Option, - provider: &mut impl TzProvider, + provider: &impl TzProvider, ) -> TemporalResult { // 1. If temporalTimeZoneLike is undefined, then // a. Let timeZone be SystemTimeZoneIdentifier(). @@ -69,3 +69,33 @@ fn system_instant() -> TemporalResult { let nanos = sys::get_system_nanoseconds()?; Instant::try_new(i128::from_u128(nanos).temporal_unwrap()?) } + +#[cfg(test)] +mod tests { + use std::thread; + use std::time::Duration as StdDuration; + + use crate::{partial::PartialDuration, tzdb::FsTzdbProvider, Duration, Now}; + + #[cfg(feature = "tzdb")] + #[test] + fn now_datetime_test() { + let provider = &FsTzdbProvider::default(); + + let now = Now::plain_date_time_with_provider(None, provider).unwrap(); + thread::sleep(StdDuration::from_secs(2)); + let then = Now::plain_date_time_with_provider(None, provider).unwrap(); + + let two_seconds = Duration::from_partial_duration(PartialDuration { + seconds: Some(2.into()), + ..Default::default() + }) + .unwrap(); + + let now_plus_two = now.add(&two_seconds, None).unwrap(); + + assert_eq!(now_plus_two.second(), then.second()); + assert_eq!(now_plus_two.minute(), then.minute()); + assert_eq!(now_plus_two.hour(), then.hour()); + } +} diff --git a/src/lib.rs b/src/lib.rs index 26a64371..35af6674 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -43,7 +43,6 @@ extern crate alloc; extern crate core; -// TODO: Support SystemTime directly / pull in OS code from std::time? #[cfg(feature = "std")] extern crate std; diff --git a/src/sys.rs b/src/sys.rs index 6342b2cf..5a074a58 100644 --- a/src/sys.rs +++ b/src/sys.rs @@ -2,9 +2,9 @@ use alloc::string::{String, ToString}; use crate::{TemporalError, TemporalResult}; -use std::time::{SystemTime, UNIX_EPOCH}; +use web_time::{SystemTime, UNIX_EPOCH}; -// TODO: Need to implement system handling for non_std. +// TODO: Need to implement SystemTime handling for non_std. /// Returns the system time in nanoseconds. pub(crate) fn get_system_nanoseconds() -> TemporalResult { diff --git a/src/tzdb.rs b/src/tzdb.rs index 068988d5..c6e00f48 100644 --- a/src/tzdb.rs +++ b/src/tzdb.rs @@ -298,7 +298,9 @@ impl Tzif { #[inline] fn get_local_record(db: &DataBlock, idx: usize) -> LocalTimeTypeRecord { - db.local_time_type_records[db.transition_types[idx]] + // NOTE: Transition type can be empty. If no transition_type exists, + // then use 0 as the default index of local_time_type_records. + db.local_time_type_records[db.transition_types.get(idx).copied().unwrap_or(0)] } #[inline]