1use crate::{Dt, Scale};
2use chrono::{DateTime, Datelike, Duration, TimeDelta, Timelike, Utc};
3use core::convert::From;
4
5impl Dt {
6 #[inline]
12 pub fn to_chrono_datetime_utc(&self) -> DateTime<Utc> {
13 DateTime::<Utc>::from_timestamp_nanos(Dt::to_i64(
14 self.target(Scale::UTC).to_unix().to_ns().0,
15 ))
16 }
17
18 pub fn from_chrono_datetime_utc(dt: DateTime<Utc>) -> Dt {
22 let yr = dt.year() as i64;
23 let mo = dt.month().clamp(1, 12) as u8;
24 let day = dt.day().clamp(1, 31) as u8;
25 let hr = dt.hour().clamp(0, 23) as u8;
26 let min = dt.minute().clamp(0, 59) as u8;
27 let sec = dt.second().clamp(0, 60) as u8;
28 let subsec_nanos = dt.nanosecond();
29 let attos = Dt::from_ns(subsec_nanos as i128, 0, Scale::TAI, Scale::TAI).to_attos();
30
31 Dt::from_ymd(yr, mo, day, Scale::UTC, hr, min, sec, Dt::to_u64(attos))
32 }
33
34 pub fn from_chrono_duration(dur: Duration) -> Dt {
36 match dur.num_nanoseconds() {
37 Some(ns) => Self::from_ns(ns as i128, 0, Scale::TAI, Scale::TAI),
38 None => {
39 let ns = if dur > Duration::zero() {
40 i64::MAX
41 } else {
42 i64::MIN
43 };
44 Self::from_ns(ns as i128, 0, Scale::TAI, Scale::TAI)
45 }
46 }
47 }
48
49 #[inline]
56 pub fn to_chrono_duration(&self) -> Duration {
57 TimeDelta::nanoseconds(Dt::to_i64(self.to_ns().0))
58 }
59}
60
61impl From<DateTime<Utc>> for Dt {
62 #[inline]
63 fn from(dt: DateTime<Utc>) -> Self {
64 Self::from_chrono_datetime_utc(dt)
65 }
66}
67
68impl From<Dt> for DateTime<Utc> {
69 #[inline]
70 fn from(dt: Dt) -> Self {
71 dt.to_chrono_datetime_utc()
72 }
73}
74
75impl From<Duration> for Dt {
76 #[inline]
77 fn from(dur: Duration) -> Self {
78 Self::from_chrono_duration(dur)
79 }
80}
81
82impl From<Dt> for Duration {
83 #[inline]
84 fn from(dt: Dt) -> Self {
85 dt.to_chrono_duration()
86 }
87}