allo_isolate/
chrono.rs

1//! chrono types
2//!
3//! based on Dart VM, microseconds unit is used
4//!
5//! recommendations below implies UTC based conversions,
6//! as these are generally easier to work with.
7//! > see [timestamp_micros](https://docs.rs/chrono/0.4.20/chrono/naive/struct.NaiveDateTime.html?search=timestamp_micros#method.timestamp_micros)
8
9use crate::{
10    ffi::{DartCObject, DartHandleFinalizer, DartTypedDataType},
11    into_dart::{free_zero_copy_buffer_i64, DartTypedDataTypeTrait},
12    IntoDart,
13};
14
15impl IntoDart for chrono::DateTime<chrono::Utc> {
16    /// on the other side of FFI, value should be reconstructed like:
17    ///
18    /// - hydrate into Dart [DateTime](https://api.dart.dev/stable/2.18.0/dart-core/DateTime/DateTime.fromMicrosecondsSinceEpoch.html)
19    ///   `DateTime.fromMicrosecondsSinceEpoch(raw, isUtc: true);`
20    ///
21    /// - hydrate into Rust [DateTime](chrono::DateTime)::<[Utc](chrono::Utc)>
22    ///   ```rust,ignore
23    ///   let s = (raw / 1_000_000) as i64;
24    ///   let ns = (raw.rem_euclid(1_000_000) * 1_000) as u32;
25    ///   chrono::DateTime::<chrono::Utc>::from_utc(
26    ///     chrono::NaiveDateTime::from_timestamp(s, ns), chrono::Utc);
27    ///   ```
28    ///
29    ///   note that it could overflow under the same conditions as of [chrono::NaiveDateTime::from_timestamp](https://docs.rs/chrono/0.4.20/chrono/naive/struct.NaiveDateTime.html#method.from_timestamp)
30    fn into_dart(self) -> DartCObject {
31        self.timestamp_micros().into_dart()
32    }
33}
34
35impl IntoDart for chrono::DateTime<chrono::Local> {
36    /// on the other side of FFI, value should be reconstructed like:
37    ///
38    /// - hydrate into Dart [DateTime](https://api.dart.dev/stable/2.18.0/dart-core/DateTime/DateTime.fromMicrosecondsSinceEpoch.html)
39    ///   `DateTime.fromMicrosecondsSinceEpoch(raw, isUtc: false);`
40    ///
41    /// - hydrate into Rust [DateTime](chrono::DateTime)::<[Local](chrono::Local)>
42    ///   ```rust,ignore
43    ///   let s = (raw / 1_000_000) as i64;
44    ///   let ns = (raw.rem_euclid(1_000_000) * 1_000) as u32;
45    ///   chrono::DateTime::<chrono::Local>::from(
46    ///     chrono::DateTime::<chrono::Utc>::from_utc(
47    ///       chrono::NaiveDateTime::from_timestamp(s, ns), chrono::Utc));
48    ///   ```
49    ///
50    ///   note that it could overflow under the same conditions as of [chrono::NaiveDateTime::from_timestamp](https://docs.rs/chrono/0.4.20/chrono/naive/struct.NaiveDateTime.html#method.from_timestamp)
51    fn into_dart(self) -> DartCObject {
52        self.timestamp_micros().into_dart()
53    }
54}
55
56impl IntoDart for chrono::NaiveDate {
57    /// on the other side of FFI, value should be reconstructed like:
58    ///
59    /// - hydrate into Dart [DateTime](https://api.dart.dev/stable/2.18.0/dart-core/DateTime/DateTime.fromMicrosecondsSinceEpoch.html)
60    ///   `DateTime.fromMicrosecondsSinceEpoch(raw, isUtc: true);`
61    ///
62    /// - hydrate into Rust [NaiveDateTime](chrono::NaiveDate)
63    ///   ```rust,ignore
64    ///   let s = (raw / 1_000_000) as i64;
65    ///   let ns = (raw.rem_euclid(1_000_000) * 1_000) as u32;
66    ///   chrono::NaiveDateTime::from_timestamp(s, ns)
67    ///   ```
68    ///
69    ///   note that it could overflow under the same conditions as of [chrono::NaiveDateTime::from_timestamp](https://docs.rs/chrono/0.4.20/chrono/naive/struct.NaiveDateTime.html#method.from_timestamp)
70    fn into_dart(self) -> DartCObject {
71        self.signed_duration_since(chrono::NaiveDate::MIN)
72            .into_dart()
73    }
74}
75
76impl IntoDart for chrono::NaiveDateTime {
77    /// on the other side of FFI, value should be reconstructed like:
78    ///
79    /// - hydrate into Dart [DateTime](https://api.dart.dev/stable/2.18.0/dart-core/DateTime/DateTime.fromMicrosecondsSinceEpoch.html)
80    ///   `DateTime.fromMicrosecondsSinceEpoch(raw, isUtc: true);`
81    ///
82    /// - hydrate into Rust [NaiveDateTime](chrono::NaiveDateTime)
83    ///   ```rust,ignore
84    ///   let s = (raw / 1_000_000) as i64;
85    ///   let ns = (raw.rem_euclid(1_000_000) * 1_000) as u32;
86    ///   chrono::NaiveDateTime::from_timestamp(s, ns)
87    ///   ```
88    ///
89    ///   note that it could overflow under the same conditions as of [chrono::NaiveDateTime::from_timestamp](https://docs.rs/chrono/0.4.20/chrono/naive/struct.NaiveDateTime.html#method.from_timestamp)
90    fn into_dart(self) -> DartCObject {
91        self.timestamp_micros().into_dart()
92    }
93}
94
95impl IntoDart for chrono::Duration {
96    /// on the other side of FFI, value should be reconstructed like:
97    ///
98    /// - hydrate into Dart [Duration](https://api.dart.dev/stable/2.18.0/dart-core/Duration/Duration.html)
99    ///   `Duration(microseconds: raw);`
100    ///
101    /// - hydrate into Rust [Duration](chrono::Duration)
102    /// `chrono::Duration::microseconds(raw);`
103    fn into_dart(self) -> DartCObject {
104        self.num_microseconds().into_dart()
105    }
106}
107
108impl IntoDart for Vec<chrono::DateTime<chrono::Utc>> {
109    fn into_dart(self) -> DartCObject {
110        self.iter()
111            .map(chrono::DateTime::<chrono::Utc>::timestamp_micros)
112            .collect::<Vec<_>>()
113            .into_dart()
114    }
115}
116
117impl<const N: usize> IntoDart for [chrono::DateTime<chrono::Utc>; N] {
118    fn into_dart(self) -> DartCObject {
119        let vec: Vec<_> = self.into();
120        vec.into_dart()
121    }
122}
123
124impl DartTypedDataTypeTrait for chrono::DateTime<chrono::Utc> {
125    fn dart_typed_data_type() -> DartTypedDataType {
126        DartTypedDataType::Int64
127    }
128
129    fn function_pointer_of_free_zero_copy_buffer() -> DartHandleFinalizer {
130        free_zero_copy_buffer_i64
131    }
132}
133
134impl IntoDart for Vec<chrono::DateTime<chrono::Local>> {
135    fn into_dart(self) -> DartCObject {
136        self.iter()
137            .map(chrono::DateTime::<chrono::Local>::timestamp_micros)
138            .collect::<Vec<_>>()
139            .into_dart()
140    }
141}
142
143impl<const N: usize> IntoDart for [chrono::DateTime<chrono::Local>; N] {
144    fn into_dart(self) -> DartCObject {
145        let vec: Vec<_> = self.into();
146        vec.into_dart()
147    }
148}
149
150impl DartTypedDataTypeTrait for chrono::DateTime<chrono::Local> {
151    fn dart_typed_data_type() -> DartTypedDataType {
152        DartTypedDataType::Int64
153    }
154
155    fn function_pointer_of_free_zero_copy_buffer() -> DartHandleFinalizer {
156        free_zero_copy_buffer_i64
157    }
158}
159
160impl IntoDart for Vec<chrono::NaiveDate> {
161    fn into_dart(self) -> DartCObject {
162        self.iter()
163            .map(|lhs| lhs.signed_duration_since(chrono::NaiveDate::MIN))
164            .collect::<Vec<_>>()
165            .into_dart()
166    }
167}
168
169impl<const N: usize> IntoDart for [chrono::NaiveDate; N] {
170    fn into_dart(self) -> DartCObject {
171        let vec: Vec<_> = self.into();
172        vec.into_dart()
173    }
174}
175
176impl DartTypedDataTypeTrait for chrono::NaiveDate {
177    fn dart_typed_data_type() -> DartTypedDataType {
178        DartTypedDataType::Int64
179    }
180
181    fn function_pointer_of_free_zero_copy_buffer() -> DartHandleFinalizer {
182        free_zero_copy_buffer_i64
183    }
184}
185
186impl IntoDart for Vec<chrono::NaiveDateTime> {
187    fn into_dart(self) -> DartCObject {
188        self.iter()
189            .map(chrono::NaiveDateTime::timestamp_micros)
190            .collect::<Vec<_>>()
191            .into_dart()
192    }
193}
194
195impl<const N: usize> IntoDart for [chrono::NaiveDateTime; N] {
196    fn into_dart(self) -> DartCObject {
197        let vec: Vec<_> = self.into();
198        vec.into_dart()
199    }
200}
201
202impl DartTypedDataTypeTrait for chrono::NaiveDateTime {
203    fn dart_typed_data_type() -> DartTypedDataType {
204        DartTypedDataType::Int64
205    }
206
207    fn function_pointer_of_free_zero_copy_buffer() -> DartHandleFinalizer {
208        free_zero_copy_buffer_i64
209    }
210}
211
212impl IntoDart for Vec<chrono::Duration> {
213    fn into_dart(self) -> DartCObject {
214        self.iter()
215            .map(chrono::Duration::num_microseconds)
216            .collect::<Vec<_>>()
217            .into_dart()
218    }
219}
220
221impl<const N: usize> IntoDart for [chrono::Duration; N] {
222    fn into_dart(self) -> DartCObject {
223        let vec: Vec<_> = self.into();
224        vec.into_dart()
225    }
226}