time_macros/
utc_datetime.rs1use std::iter::Peekable;
2
3use proc_macro::{TokenStream, token_stream};
4use time_core::unit::*;
5
6use crate::date::Date;
7use crate::error::Error;
8use crate::time::Time;
9use crate::to_tokens::ToTokenStream;
10use crate::{date, time};
11
12pub(crate) struct UtcDateTime {
13 pub(crate) date: Date,
14 pub(crate) time: Time,
15}
16
17impl UtcDateTime {
18 pub(crate) const fn to_timestamp(&self) -> (i64, u32) {
19 const UNIX_EPOCH_JULIAN_DAY: i64 = 2_440_588;
20
21 let julian_day = {
22 let (year, ordinal) = (self.date.year, self.date.ordinal);
23 let adj_year = year + 999_999;
24 let century = adj_year / 100;
25
26 let days_before_year = (1461 * adj_year as i64 / 4) as i32 - century + century / 4;
27 days_before_year + ordinal as i32 - 363_521_075
28 };
29
30 let days = (julian_day as i64 - UNIX_EPOCH_JULIAN_DAY) * Second::per_t::<i64>(Day);
31 let hours = self.time.hour as i64 * Second::per_t::<i64>(Hour);
32 let minutes = self.time.minute as i64 * Second::per_t::<i64>(Minute);
33 let seconds = self.time.second as i64;
34
35 (days + hours + minutes + seconds, self.time.nanosecond)
36 }
37}
38
39pub(crate) fn parse(chars: &mut Peekable<token_stream::IntoIter>) -> Result<UtcDateTime, Error> {
40 let date = date::parse(chars)?;
41 let time = time::parse(chars)?;
42
43 if let Some(token) = chars.peek() {
44 return Err(Error::UnexpectedToken {
45 tree: token.clone(),
46 });
47 }
48
49 Ok(UtcDateTime { date, time })
50}
51
52impl ToTokenStream for UtcDateTime {
53 fn append_to(self, ts: &mut TokenStream) {
54 quote_append! { ts
55 ::time::UtcDateTime::new(
56 #S(self.date),
57 #S(self.time),
58 )
59 }
60 }
61}