1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
use crate::datum::time::USECS_PER_SEC;
use crate::{direct_function_call_as_datum, pg_sys, FromDatum, IntoDatum, TimestampWithTimeZone};
use std::ops::{Deref, DerefMut};
use time::PrimitiveDateTime;
#[derive(Debug)]
pub struct Timestamp(time::PrimitiveDateTime);
impl FromDatum for Timestamp {
#[inline]
unsafe fn from_datum(datum: pg_sys::Datum, is_null: bool, typoid: u32) -> Option<Timestamp> {
let ts: Option<TimestampWithTimeZone> =
TimestampWithTimeZone::from_datum(datum, is_null, typoid);
match ts {
None => None,
Some(ts) => {
let date = ts.date();
let time = ts.time();
Some(Timestamp(PrimitiveDateTime::new(date, time)))
}
}
}
}
impl IntoDatum for Timestamp {
#[inline]
fn into_datum(self) -> Option<pg_sys::Datum> {
let year = self.year();
let month = self.month() as i32;
let mday = self.day() as i32;
let hour = self.hour() as i32;
let minute = self.minute() as i32;
let second = self.second() as f64 + (self.microsecond() as f64 / USECS_PER_SEC as f64);
direct_function_call_as_datum(
pg_sys::make_timestamp,
vec![
year.into_datum(),
month.into_datum(),
mday.into_datum(),
hour.into_datum(),
minute.into_datum(),
second.into_datum(),
],
)
}
fn type_oid() -> u32 {
pg_sys::TIMESTAMPOID
}
}
impl Timestamp {
pub fn new(timestamp: time::PrimitiveDateTime) -> Self {
Timestamp(timestamp)
}
}
impl Deref for Timestamp {
type Target = time::PrimitiveDateTime;
fn deref(&self) -> &Self::Target {
&self.0
}
}
impl DerefMut for Timestamp {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.0
}
}
impl serde::Serialize for Timestamp {
fn serialize<S>(
&self,
serializer: S,
) -> std::result::Result<<S as serde::Serializer>::Ok, <S as serde::Serializer>::Error>
where
S: serde::Serializer,
{
if self.millisecond() > 0 {
serializer.serialize_str(
&self.format(&format!("%Y-%m-%dT%H:%M:%S.{}-00", self.millisecond())),
)
} else {
serializer.serialize_str(&self.format("%Y-%m-%dT%H:%M:%S-00"))
}
}
}