Skip to main content

tank_core/
as_value.rs

1#![allow(unused_imports)]
2use crate::{
3    Error, FixedDecimal, Interval, Passive, Result, Value, consume_while, extract_number,
4    month_to_number, number_to_month, print_date, print_timer, truncate_long,
5};
6use anyhow::Context;
7#[cfg(feature = "chrono")]
8use chrono::{Datelike, Timelike};
9use rust_decimal::{Decimal, prelude::FromPrimitive, prelude::ToPrimitive};
10use std::{
11    any, array,
12    borrow::Cow,
13    cell::{Cell, RefCell},
14    collections::{BTreeMap, HashMap, LinkedList, VecDeque},
15    hash::Hash,
16    rc::Rc,
17    sync::{Arc, RwLock},
18};
19use time::{Month, PrimitiveDateTime, Time, format_description::parse_borrowed};
20use uuid::Uuid;
21
22/// Bidirectional conversion between Rust types and `Value`.
23pub trait AsValue {
24    /// Return NULL variant.
25    fn as_empty_value() -> Value;
26    /// Convert to `Value`.
27    fn as_value(self) -> Value;
28    /// Convert from `Value`.
29    fn try_from_value(value: Value) -> Result<Self>
30    where
31        Self: Sized;
32    /// Parse string.
33    fn parse(input: impl AsRef<str>) -> Result<Self>
34    where
35        Self: Sized,
36    {
37        Err(Error::msg(format!(
38            "Cannot parse '{}' as {} (the parse method is not implemented)",
39            truncate_long!(input.as_ref()),
40            any::type_name::<Self>()
41        )))
42    }
43}
44
45impl AsValue for Value {
46    fn as_empty_value() -> Value {
47        Value::Null
48    }
49    fn as_value(self) -> Value {
50        self
51    }
52    fn try_from_value(value: Value) -> Result<Self>
53    where
54        Self: Sized,
55    {
56        Ok(value)
57    }
58}
59
60impl From<&'static str> for Value {
61    fn from(value: &'static str) -> Self {
62        Value::Varchar(Some(value.into()))
63    }
64}
65
66macro_rules! impl_as_value {
67    ($source:ty, $destination:path $(, $pat_rest:pat => $expr_rest:expr)* $(,)?) => {
68        impl AsValue for $source {
69            fn as_empty_value() -> Value {
70                $destination(None)
71            }
72            fn as_value(self) -> Value {
73                $destination(Some(self as _))
74            }
75            fn try_from_value(value: Value) -> Result<Self> {
76                match value {
77                    $destination(Some(v), ..) => Ok(v as _),
78                    $($pat_rest => $expr_rest,)*
79                    #[allow(unreachable_patterns)]
80                    Value::Int32(Some(v), ..) => {
81                        let mut max = <$source>::MAX as i128;
82                        if max < 0 {
83                            max = i128::MAX;
84                        }
85                        if (v as i128).clamp(<$source>::MIN as _, max as _) != v as i128 {
86                            return Err(Error::msg(format!(
87                                "Value {v}: i32 is out of range for {}",
88                                any::type_name::<Self>(),
89                            )));
90                        }
91                        Ok(v as $source)
92                    }
93                    #[allow(unreachable_patterns)]
94                    // SQL INTEGER becomes i64
95                    Value::Int64(Some(v), ..) => {
96                        let mut max = <$source>::MAX as i128;
97                        if max < 0 {
98                            max = i128::MAX;
99                        }
100                        if (v as i128).clamp(<$source>::MIN as _, max) != v as i128 {
101                            return Err(Error::msg(format!(
102                                "Value {v}: i64 is out of range for {}",
103                                any::type_name::<Self>(),
104                            )));
105                        }
106                        Ok(v as $source)
107                    }
108                    #[allow(unreachable_patterns)]
109                    // SQL VARINT becomes i128
110                    Value::Int128(Some(v), ..) => {
111                        let mut max = <$source>::MAX as i128;
112                        if max < 0 {
113                            max = i128::MAX;
114                        }
115                        if v.clamp(<$source>::MIN as _, max) != v as i128 {
116                            return Err(Error::msg(format!(
117                                "Value {v}: i128 is out of range for {}",
118                                any::type_name::<Self>(),
119                            )));
120                        }
121                        Ok(v as _)
122                    },
123                    #[allow(unreachable_patterns)]
124                    // SQL Generic floating point value
125                    Value::Float64(Some(v), ..) => {
126                        if v.is_finite() && v.fract() == 0.0 {
127                            return Self::try_from_value(Value::Int64(Some(v as _)))
128                        }
129                        Err(Error::msg(format!("Value {v}: f64 does not fit into a integer")))
130                    },
131                    // This is needed to allow integer keys in maps, in some drivers the maps keys are strings only
132                    Value::Varchar(Some(ref v), ..) => <Self as AsValue>::parse(v).with_context(|| {
133                        format!("While parsing a {} from `{}`", any::type_name::<Self>(), v)
134                    }),
135                    Value::Json(Some(serde_json::Value::Number(v)), ..) => {
136                        let integer = v.as_i128().or_else(|| {
137                            if let Some(v) = v.as_f64() && v.fract() == 0.0 {
138                                return Some(v.trunc() as i128);
139                            }
140                            None
141                        });
142                        let mut max = <$source>::MAX as i128;
143                        if max < 0 {
144                            max = i128::MAX;
145                        }
146                        if let Some(v) = integer
147                            && v.clamp(<$source>::MIN as _, max) == v as i128 {
148                            return Ok(v as $source);
149                        }
150                        Err(Error::msg(format!(
151                            "Value {v} from json number is out of range for {} (extracted integer is: {integer:?})",
152                            any::type_name::<Self>(),
153                        )))
154                    }
155                    // This is needed to allow integer keys in maps, in some drivers the maps are json objects
156                    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
157                    Value::Unknown(Some(ref v), ..) => Self::parse(v).with_context(|| {
158                        format!("While parsing a {} from `{}`", any::type_name::<Self>(), v)
159                    }),
160                    _ => Err(Error::msg(format!(
161                        "Cannot convert {value:?} to {}",
162                        any::type_name::<Self>(),
163                    ))),
164                }
165            }
166            fn parse(input: impl AsRef<str>) -> Result<Self> {
167                input.as_ref().parse::<Self>().map_err(Into::into)
168            }
169        }
170    };
171}
172
173impl_as_value!(
174    i8,
175    Value::Int8,
176    Value::UInt8(Some(v), ..) => Ok(v as _),
177    Value::Int16(Some(v), ..) => {
178        let result = v as i8;
179        if result as i16 != v {
180            return Err(Error::msg(format!("Value {v}: i16 is out of range for i8")));
181        }
182        Ok(result)
183    },
184);
185
186impl_as_value!(
187    i16,
188    Value::Int16,
189    Value::Int8(Some(v), ..) => Ok(v as _),
190    Value::UInt16(Some(v), ..) => Ok(v as _),
191    Value::UInt8(Some(v), ..) => Ok(v as _),
192);
193
194impl_as_value!(
195    i32,
196    Value::Int32,
197    Value::Int16(Some(v), ..) => Ok(v as _),
198    Value::Int8(Some(v), ..) => Ok(v as _),
199    Value::UInt32(Some(v), ..) => Ok(v as _),
200    Value::UInt16(Some(v), ..) => Ok(v as _),
201    Value::UInt8(Some(v), ..) => Ok(v as _),
202    Value::Decimal(Some(v), ..) => {
203        let error = Error::msg(format!("Value {v}: Decimal does not fit into i32"));
204        if !v.is_integer() {
205            return Err(error.context("The value is not an integer"));
206        }
207        v.to_i32().ok_or(error)
208    }
209);
210
211impl_as_value!(
212    i64,
213    Value::Int64,
214    Value::Int32(Some(v), ..) => Ok(v as _),
215    Value::Int16(Some(v), ..) => Ok(v as _),
216    Value::Int8(Some(v), ..) => Ok(v as _),
217    Value::UInt64(Some(v), ..) => Ok(v as _),
218    Value::UInt32(Some(v), ..) => Ok(v as _),
219    Value::UInt16(Some(v), ..) => Ok(v as _),
220    Value::UInt8(Some(v), ..) => Ok(v as _),
221    Value::Decimal(Some(v), ..) => {
222        let error = Error::msg(format!("Value {v}: Decimal does not fit into i64"));
223        if !v.is_integer() {
224            return Err(error.context("The value is not an integer"));
225        }
226        v.to_i64().ok_or(error)
227    }
228);
229
230impl_as_value!(
231    i128,
232    Value::Int128,
233    Value::Int64(Some(v), ..) => Ok(v as _),
234    Value::Int32(Some(v), ..) => Ok(v as _),
235    Value::Int16(Some(v), ..) => Ok(v as _),
236    Value::Int8(Some(v), ..) => Ok(v as _),
237    Value::UInt128(Some(v), ..) => Ok(v as _),
238    Value::UInt64(Some(v), ..) => Ok(v as _),
239    Value::UInt32(Some(v), ..) => Ok(v as _),
240    Value::UInt16(Some(v), ..) => Ok(v as _),
241    Value::UInt8(Some(v), ..) => Ok(v as _),
242    Value::Decimal(Some(v), ..) => {
243        let error = Error::msg(format!("Value {v}: Decimal does not fit into i128"));
244        if !v.is_integer() {
245            return Err(error.context("The value is not an integer"));
246        }
247        v.to_i128().ok_or(error)
248    }
249);
250
251impl_as_value!(
252    isize,
253    Value::Int64,
254    Value::Int32(Some(v), ..) => Ok(v as _),
255    Value::Int16(Some(v), ..) => Ok(v as _),
256    Value::Int8(Some(v), ..) => Ok(v as _),
257    Value::UInt64(Some(v), ..) => Ok(v as _),
258    Value::UInt32(Some(v), ..) => Ok(v as _),
259    Value::UInt16(Some(v), ..) => Ok(v as _),
260    Value::UInt8(Some(v), ..) => Ok(v as _),
261    Value::Decimal(Some(v), ..) => {
262        let error = Error::msg(format!("Value {v}: Decimal does not fit into i64"));
263        if !v.is_integer() {
264            return Err(error.context("The value is not an integer"));
265        }
266        v.to_isize().ok_or(error)
267    }
268);
269
270impl_as_value!(
271    u8,
272    Value::UInt8,
273    Value::Int16(Some(v), ..) => {
274        v.to_u8().ok_or(Error::msg(format!("Value {v}: i16 is out of range for u8")))
275    }
276);
277
278impl_as_value!(
279    u16,
280    Value::UInt16,
281    Value::UInt8(Some(v), ..) => Ok(v as _),
282    Value::Int32(Some(v), ..) => {
283        let result = v as u16;
284        if result as i32 != v {
285            return Err(Error::msg(format!("Value {v}: i32 is out of range for u16")));
286        }
287        Ok(result)
288    }
289);
290
291impl_as_value!(
292    u32,
293    Value::UInt32,
294    Value::UInt16(Some(v), ..) => Ok(v as _),
295    Value::UInt8(Some(v), ..) => Ok(v as _),
296);
297
298impl_as_value!(
299    u64,
300    Value::UInt64,
301    Value::UInt32(Some(v), ..) => Ok(v as _),
302    Value::UInt16(Some(v), ..) => Ok(v as _),
303    Value::UInt8(Some(v), ..) => Ok(v as _),
304    Value::Decimal(Some(v), ..) => {
305        let error = Error::msg(format!("Value {v}: Decimal does not fit into u64"));
306        if !v.is_integer() {
307            return Err(error.context("The value is not an integer"));
308        }
309        v.to_u64().ok_or(error)
310    }
311);
312
313impl_as_value!(
314    u128,
315    Value::UInt128,
316    Value::UInt64(Some(v), ..) => Ok(v as _),
317    Value::UInt32(Some(v), ..) => Ok(v as _),
318    Value::UInt16(Some(v), ..) => Ok(v as _),
319    Value::UInt8(Some(v), ..) => Ok(v as _),
320    Value::Decimal(Some(v), ..) => {
321        let error = Error::msg(format!("Value {v}: Decimal does not fit into u128"));
322        if !v.is_integer() {
323            return Err(error.context("The value is not an integer"));
324        }
325        v.to_u128().ok_or(error)
326    }
327);
328
329impl_as_value!(
330    usize,
331    Value::UInt64,
332    Value::UInt32(Some(v), ..) => Ok(v as _),
333    Value::UInt16(Some(v), ..) => Ok(v as _),
334    Value::UInt8(Some(v), ..) => Ok(v as _),
335    Value::Decimal(Some(v), ..) => {
336        let error = Error::msg(format!("Value {v}: Decimal does not fit into u64"));
337        if !v.is_integer() {
338            return Err(error.context("The value is not an integer"));
339        }
340        v.to_usize().ok_or(error)
341    }
342);
343
344macro_rules! impl_as_value {
345    ($source:ty, $destination:path, $extract:expr $(, $pat_rest:pat => $expr_rest:expr)* $(,)?) => {
346        impl AsValue for $source {
347            fn as_empty_value() -> Value {
348                $destination(None)
349            }
350            fn as_value(self) -> Value {
351                $destination(Some(self.into()))
352            }
353            fn try_from_value(value: Value) -> Result<Self> {
354                match value {
355                    $destination(Some(v), ..) => Ok(v.into()),
356                    $($pat_rest => $expr_rest,)*
357                    #[allow(unreachable_patterns)]
358                    Value::Varchar(Some(ref v), ..) => {
359                        <Self as AsValue>::parse(v).with_context(|| {
360                            format!("While parsing a {} from `{}`", any::type_name::<Self>(), v)
361                        })
362                    }
363                    Value::Unknown(Some(ref v), ..) => {
364                        <Self as AsValue>::parse(v).with_context(|| {
365                            format!("While parsing a {} from `{}`", any::type_name::<Self>(), v)
366                        })
367                    }
368                    _ => Err(Error::msg(format!(
369                        "Cannot convert {value:?} to {}",
370                        any::type_name::<Self>(),
371                    ))),
372                }
373            }
374            fn parse(input: impl AsRef<str>) -> Result<Self> {
375                $extract(input.as_ref())
376            }
377        }
378    };
379}
380
381impl_as_value!(
382    bool,
383    Value::Boolean,
384    |input: &str| {
385        match input {
386            x if x.eq_ignore_ascii_case("true") || x.eq_ignore_ascii_case("t") || x.eq("1") => Ok(true),
387            x if x.eq_ignore_ascii_case("false") || x.eq_ignore_ascii_case("f") || x.eq("0") => Ok(false),
388            _  => return Err(Error::msg(format!("Cannot parse boolean from `{input}`")))
389        }
390    },
391    Value::Int8(Some(v), ..) => Ok(v != 0),
392    Value::Int16(Some(v), ..) => Ok(v != 0),
393    Value::Int32(Some(v), ..) => Ok(v != 0),
394    Value::Int64(Some(v), ..) => Ok(v != 0),
395    Value::Int128(Some(v), ..) => Ok(v != 0),
396    Value::UInt8(Some(v), ..) => Ok(v != 0),
397    Value::UInt16(Some(v), ..) => Ok(v != 0),
398    Value::UInt32(Some(v), ..) => Ok(v != 0),
399    Value::UInt64(Some(v), ..) => Ok(v != 0),
400    Value::UInt128(Some(v), ..) => Ok(v != 0),
401    Value::Json(Some(serde_json::Value::Bool(v)), ..) => Ok(v),
402    Value::Json(Some(serde_json::Value::Number(v)), ..) => {
403        let n = v.as_i64();
404        if n == Some(0) {
405            Ok(false)
406        } else if n == Some(1) {
407            Ok(true)
408        } else {
409            Err(Error::msg(format!("Cannot convert json number `{v:?}` into bool")))
410        }
411    },
412);
413
414impl_as_value!(
415    f32,
416    Value::Float32,
417    |input: &str| Ok(input.parse::<f32>()?),
418    Value::Float64(Some(v), ..) => Ok(v as _),
419    Value::Decimal(Some(v), ..) => Ok(v.try_into()?),
420    Value::Json(Some(serde_json::Value::Number(v)), ..) => {
421        let Some(v) = v.as_f64() else {
422            return Err(Error::msg(format!("Cannot convert json number `{v:?}` into f32")));
423        };
424        Ok(v as _)
425    }
426);
427
428impl_as_value!(
429    f64,
430    Value::Float64,
431    |input: &str| Ok(input.parse::<f64>()?),
432    Value::Float32(Some(v), ..) => Ok(v as _),
433    Value::Decimal(Some(v), ..) => Ok(v.try_into()?),
434    Value::Json(Some(serde_json::Value::Number(v)), ..) => {
435        let Some(v) = v.as_f64() else {
436            return Err(Error::msg(format!("Cannot convert json number `{v:?}` into f32")));
437        };
438        Ok(v)
439    }
440);
441
442impl_as_value!(
443    char,
444    Value::Char,
445    |input: &str| {
446        if input.len() != 1 {
447            return Err(Error::msg(format!("Cannot convert `{input:?}` into a char")))
448        }
449        Ok(input.chars().next().expect("Should have one character"))
450    },
451    Value::Varchar(Some(v), ..) => {
452        if v.len() != 1 {
453            return Err(Error::msg(format!(
454                "Cannot convert varchar `{}` into a char because it has more than one character",
455                truncate_long!(v)
456            )))
457        }
458        Ok(v.chars().next().unwrap())
459    },
460    Value::Json(Some(serde_json::Value::String(v)), ..) => {
461        if v.len() != 1 {
462            return Err(Error::msg(format!(
463                "Cannot convert json `{}` into a char because it has more than one character",
464                truncate_long!(v)
465            )))
466        }
467        Ok(v.chars().next().unwrap())
468    }
469);
470
471impl_as_value!(
472    String,
473    Value::Varchar,
474    |input: &str| {
475        Ok(input.into())
476    },
477    Value::Int8(Some(v), ..) => Ok(v.to_string()),
478    Value::Int16(Some(v), ..) => Ok(v.to_string()),
479    Value::Int32(Some(v), ..) => Ok(v.to_string()),
480    Value::Int64(Some(v), ..) => Ok(v.to_string()),
481    Value::Int128(Some(v), ..) => Ok(v.to_string()),
482    Value::UInt8(Some(v), ..) => Ok(v.to_string()),
483    Value::UInt16(Some(v), ..) => Ok(v.to_string()),
484    Value::UInt32(Some(v), ..) => Ok(v.to_string()),
485    Value::UInt64(Some(v), ..) => Ok(v.to_string()),
486    Value::UInt128(Some(v), ..) => Ok(v.to_string()),
487    Value::Float32(Some(v), ..) => Ok(v.to_string()),
488    Value::Float64(Some(v), ..) => Ok(v.to_string()),
489    Value::Decimal(Some(v), ..) => Ok(v.to_string()),
490    Value::Char(Some(v), ..) => Ok(v.into()),
491    Value::Date(Some(v), ..) => {
492        let mut out = String::new();
493        print_date(&mut out, "", &v);
494        Ok(out)
495    },
496    Value::Time(Some(v), ..) => {
497        let mut out = String::new();
498        print_timer(&mut out, "", v.hour() as _, v.minute(), v.second(), v.nanosecond());
499        Ok(out)
500    },
501    Value::Timestamp(Some(v), ..) => {
502        let date = v.date();
503        let time = v.time();
504        let mut out = String::new();
505        print_date(&mut out, "", &date);
506        out.push(' ');
507        print_timer(&mut out, "", time.hour() as _ , time.minute(), time.second(), time.nanosecond());
508        Ok(out)
509    },
510    Value::TimestampWithTimezone(Some(v), ..) => {
511        let date = v.date();
512        let time = v.time();
513        let mut out = String::new();
514        print_date(&mut out, "", &date);
515        out.push(' ');
516        print_timer(&mut out, "", time.hour() as _, time.minute(), time.second(), time.nanosecond());
517        let (h, m, s) = v.offset().as_hms();
518        out.push(' ');
519        if h >= 0 {
520            out.push('+');
521        } else {
522            out.push('-');
523        }
524        let offset = match Time::from_hms(h.abs() as _, m.abs() as _, s.abs() as _){
525            Ok(v) => v,
526            Err(e) => return Err(Error::new(e)),
527        };
528        print_timer(&mut out, "", offset.hour() as _, offset.minute(), offset.second(), offset.nanosecond());
529        Ok(out)
530    },
531    Value::Uuid(Some(v), ..) => Ok(v.to_string()),
532    Value::Json(Some(serde_json::Value::String(v)), ..) => Ok(v),
533);
534
535impl_as_value!(Box<[u8]>, Value::Blob, |mut input: &str| {
536    if input.starts_with("\\x") {
537        input = &input[2..];
538    }
539    let filter_x = input.contains('x');
540    let result = if filter_x {
541        hex::decode(input.chars().filter(|c| *c != 'x').collect::<String>())
542    } else {
543        hex::decode(input)
544    }
545    .map(Into::into)
546    .context(format!(
547        "While decoding `{}` as {}",
548        truncate_long!(input),
549        any::type_name::<Self>()
550    ))?;
551    Ok(result)
552});
553
554impl_as_value!(
555    Interval,
556    Value::Interval,
557    |mut input: &str| {
558        let context = || {
559            Error::msg(format!(
560                "Cannot parse interval from `{}`",
561                truncate_long!(input)
562            ))
563            .into()
564        };
565        match input.chars().peekable().peek() {
566            Some(v) if *v == '"' || *v == '\'' => {
567                input = &input[1..];
568                if !input.ends_with(*v) {
569                    return Err(context());
570                }
571                input = input.trim_end_matches(*v);
572            }
573            _ => {}
574        };
575        let mut interval = Interval::ZERO;
576        loop {
577            let mut cur = input;
578            let Ok(count) = extract_number::<true>(&mut cur).parse::<i128>() else {
579                break;
580            };
581            cur = cur.trim_start();
582            let unit = consume_while(&mut cur, char::is_ascii_alphabetic);
583            if unit.is_empty() {
584                break;
585            }
586            match unit {
587                x if x.eq_ignore_ascii_case("y")
588                    || x.eq_ignore_ascii_case("year")
589                    || x.eq_ignore_ascii_case("years") =>
590                {
591                    interval += Interval::from_years(count as _)
592                }
593                x if x.eq_ignore_ascii_case("mon")
594                    || x.eq_ignore_ascii_case("mons")
595                    || x.eq_ignore_ascii_case("month")
596                    || x.eq_ignore_ascii_case("months") =>
597                {
598                    interval += Interval::from_months(count as _)
599                }
600                x if x.eq_ignore_ascii_case("d")
601                    || x.eq_ignore_ascii_case("day")
602                    || x.eq_ignore_ascii_case("days") =>
603                {
604                    interval += Interval::from_days(count as _)
605                }
606                x if x.eq_ignore_ascii_case("h")
607                    || x.eq_ignore_ascii_case("hour")
608                    || x.eq_ignore_ascii_case("hours") =>
609                {
610                    interval += Interval::from_hours(count as _)
611                }
612                x if x.eq_ignore_ascii_case("min")
613                    || x.eq_ignore_ascii_case("mins")
614                    || x.eq_ignore_ascii_case("minute")
615                    || x.eq_ignore_ascii_case("minutes") =>
616                {
617                    interval += Interval::from_mins(count as _)
618                }
619                x if x.eq_ignore_ascii_case("s")
620                    || x.eq_ignore_ascii_case("sec")
621                    || x.eq_ignore_ascii_case("secs")
622                    || x.eq_ignore_ascii_case("second")
623                    || x.eq_ignore_ascii_case("seconds") =>
624                {
625                    interval += Interval::from_secs(count as _)
626                }
627                x if x.eq_ignore_ascii_case("micro")
628                    || x.eq_ignore_ascii_case("micros")
629                    || x.eq_ignore_ascii_case("microsecond")
630                    || x.eq_ignore_ascii_case("microseconds") =>
631                {
632                    interval += Interval::from_micros(count as _)
633                }
634                x if x.eq_ignore_ascii_case("ns")
635                    || x.eq_ignore_ascii_case("nano")
636                    || x.eq_ignore_ascii_case("nanos")
637                    || x.eq_ignore_ascii_case("nanosecond")
638                    || x.eq_ignore_ascii_case("nanoseconds") =>
639                {
640                    interval += Interval::from_nanos(count as _)
641                }
642                _ => return Err(context()),
643            }
644            input = cur.trim_start();
645        }
646        let neg = if Some('-') == input.chars().next() {
647            input = input[1..].trim_ascii_start();
648            true
649        } else {
650            false
651        };
652        let mut time_interval = Interval::ZERO;
653        let num = extract_number::<true>(&mut input);
654        if !num.is_empty() {
655            let num = num.parse::<u64>().with_context(context)?;
656            time_interval += Interval::from_hours(num as _);
657            if Some(':') == input.chars().next() {
658                input = &input[1..];
659                let num = extract_number::<false>(&mut input).parse::<u64>()?;
660                if input.is_empty() {
661                    return Err(context());
662                }
663                time_interval += Interval::from_mins(num as _);
664                if Some(':') == input.chars().next() {
665                    input = &input[1..];
666                    let num = extract_number::<false>(&mut input)
667                        .parse::<u64>()
668                        .with_context(context)?;
669                    time_interval += Interval::from_secs(num as _);
670                    if Some('.') == input.chars().next() {
671                        input = &input[1..];
672                        let len = input.len();
673                        let mut num = extract_number::<true>(&mut input)
674                            .parse::<i128>()
675                            .with_context(context)?;
676                        let magnitude = (len - 1) / 3;
677                        num *= 10_i128.pow(2 - (len + 2) as u32 % 3);
678                        match magnitude {
679                            0 => time_interval += Interval::from_millis(num),
680                            1 => time_interval += Interval::from_micros(num),
681                            2 => time_interval += Interval::from_nanos(num),
682                            _ => return Err(context()),
683                        }
684                    }
685                }
686            }
687            if neg {
688                interval -= time_interval;
689            } else {
690                interval += time_interval;
691            }
692        }
693        if !input.is_empty() {
694            return Err(context());
695        }
696        Ok(interval)
697    },
698    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
699);
700
701impl_as_value!(
702    std::time::Duration,
703    Value::Interval,
704    |v| <Interval as AsValue>::parse(v).map(Into::into),
705    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
706);
707
708impl_as_value!(
709    time::Duration,
710    Value::Interval,
711    |v| <Interval as AsValue>::parse(v).map(Into::into),
712    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
713);
714
715impl_as_value!(
716    Uuid,
717    Value::Uuid,
718    |input: &str| {
719        let uuid = Uuid::parse_str(input).with_context(|| {
720            format!(
721                "Cannot parse a uuid value from `{}`",
722                truncate_long!(input)
723            )
724        })?;
725        Ok(uuid)
726    },
727    Value::Varchar(Some(v), ..) => <Self as AsValue>::parse(v),
728    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
729);
730
731macro_rules! parse_time {
732    ($value: ident, $($formats:literal),+ $(,)?) => {
733        'value: {
734            let context = || Error::msg(format!(
735                "Cannot parse `{}` as {}",
736                truncate_long!($value),
737                any::type_name::<Self>()
738            ));
739            for format in [$($formats,)+] {
740                let format = parse_borrowed::<2>(format)?;
741                let mut parsed = time::parsing::Parsed::new();
742                let remaining = parsed.parse_items($value.as_bytes(), &format);
743                if let Ok(remaining) = remaining {
744                    let result = parsed.try_into().with_context(context)?;
745                    $value = &$value[($value.len() - remaining.len())..];
746                    break 'value Ok(result);
747                }
748            }
749            Err(context())
750        }
751    }
752}
753
754impl_as_value!(
755    time::Date,
756    Value::Date,
757    |input: &str| {
758        let mut value = input;
759        let mut result: time::Date = parse_time!(value, "[year]-[month]-[day]")?;
760        {
761            let mut attempt = value.trim_start();
762            let suffix = consume_while(&mut attempt, char::is_ascii_alphabetic);
763            if suffix.eq_ignore_ascii_case("bc") {
764                result =
765                    time::Date::from_calendar_date(-(result.year() - 1), result.month(), result.day())?;
766                value = attempt;
767            }
768            if suffix.eq_ignore_ascii_case("ad") {
769                value = attempt
770            }
771        }
772        if !value.is_empty() {
773            return Err(Error::msg(format!("Cannot parse `{}` as time::Date", truncate_long!(input))))
774        }
775        Ok(result)
776    },
777    Value::Varchar(Some(v), ..) => <Self as AsValue>::parse(v),
778    Value::Timestamp(Some(v), ..) => {
779        if v.time() != time::Time::MIDNIGHT {
780            return Err(Error::msg(format!("Timestamp {v:?} cannot be converted to date because the time part is not midnight")))
781        }
782        Ok(v.date())
783    },
784    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
785);
786
787impl_as_value!(
788    time::Time,
789    Value::Time,
790    |mut input: &str| {
791        let result: time::Time = parse_time!(
792            input,
793            "[hour]:[minute]:[second].[subsecond]",
794            "[hour]:[minute]:[second]",
795            "[hour]:[minute]",
796        )?;
797        if !input.is_empty() {
798            return Err(Error::msg(format!("Cannot parse `{}` as time::Time", truncate_long!(input))))
799        }
800        Ok(result)
801    },
802    Value::Interval(Some(v), ..) => {
803        let (h, m, s, ns) = v.as_hmsns();
804        time::Time::from_hms_nano(h as _, m, s, ns,)
805            .map_err(|e| Error::msg(format!("Cannot convert interval `{v:?}` into time: {e:?}")))
806    },
807    Value::Varchar(Some(v), ..) => <Self as AsValue>::parse(v),
808    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
809);
810
811impl_as_value!(
812    time::PrimitiveDateTime,
813    Value::Timestamp,
814    |mut input: &str| {
815        let result: time::PrimitiveDateTime = parse_time!(
816            input,
817            "[year]-[month]-[day]T[hour]:[minute]:[second].[subsecond]",
818            "[year]-[month]-[day]T[hour]:[minute]:[second]",
819            "[year]-[month]-[day]T[hour]:[minute]",
820            "[year]-[month]-[day] [hour]:[minute]:[second].[subsecond]",
821            "[year]-[month]-[day] [hour]:[minute]:[second]",
822            "[year]-[month]-[day] [hour]:[minute]",
823        )?;
824        if !input.is_empty() {
825            return Err(Error::msg(format!("Cannot parse `{}` as time::PrimitiveDateTime", truncate_long!(input))))
826        }
827        Ok(result)
828    },
829    Value::Varchar(Some(v), ..) => <Self as AsValue>::parse(v),
830    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
831);
832
833impl_as_value!(
834    time::OffsetDateTime,
835    Value::TimestampWithTimezone,
836    |mut input: &str| {
837        if let Ok::<time::OffsetDateTime, _>(result) = parse_time!(
838            input,
839            "[year]-[month]-[day]T[hour]:[minute]:[second].[subsecond][offset_hour sign:mandatory]:[offset_minute]",
840            "[year]-[month]-[day]T[hour]:[minute]:[second].[subsecond][offset_hour sign:mandatory]",
841            "[year]-[month]-[day]T[hour]:[minute]:[second][offset_hour sign:mandatory]:[offset_minute]",
842            "[year]-[month]-[day]T[hour]:[minute]:[second][offset_hour sign:mandatory]",
843            "[year]-[month]-[day]T[hour]:[minute][offset_hour sign:mandatory]:[offset_minute]",
844            "[year]-[month]-[day]T[hour]:[minute][offset_hour sign:mandatory]",
845            "[year]-[month]-[day] [hour]:[minute]:[second].[subsecond][offset_hour sign:mandatory]:[offset_minute]",
846            "[year]-[month]-[day] [hour]:[minute]:[second].[subsecond][offset_hour sign:mandatory]",
847            "[year]-[month]-[day] [hour]:[minute]:[second][offset_hour sign:mandatory]:[offset_minute]",
848            "[year]-[month]-[day] [hour]:[minute]:[second][offset_hour sign:mandatory]",
849            "[year]-[month]-[day] [hour]:[minute][offset_hour sign:mandatory]:[offset_minute]",
850            "[year]-[month]-[day] [hour]:[minute][offset_hour sign:mandatory]",
851        ) {
852            return Ok(result);
853        }
854        if let Ok(result) = <PrimitiveDateTime as AsValue>::parse(input).map(|v| v.assume_utc()) {
855            return Ok(result);
856        }
857        Err(Error::msg(format!("Cannot parse `{}` as time::OffsetDateTime", truncate_long!(input))))
858    },
859    Value::Timestamp(Some(timestamp), ..) => Ok(timestamp.assume_utc()),
860    Value::Varchar(Some(v), ..) => <Self as AsValue>::parse(v),
861    Value::Json(Some(serde_json::Value::String(ref v)), ..) => <Self as AsValue>::parse(v),
862);
863
864#[cfg(feature = "chrono")]
865impl AsValue for chrono::NaiveDate {
866    fn as_empty_value() -> Value {
867        Value::Date(None)
868    }
869    fn as_value(self) -> Value {
870        Value::Date(
871            'date: {
872                time::Date::from_calendar_date(
873                    self.year(),
874                    number_to_month!(
875                        self.month(),
876                        break 'date Err(Error::msg(format!(
877                            "Unexpected month value {}",
878                            self.month()
879                        )))
880                    ),
881                    self.day() as _,
882                )
883                .map_err(Into::into)
884            }
885            .inspect_err(|e| {
886                log::error!("Could not create a Value::Date from chrono::NaiveDate: {e:?}");
887            })
888            .ok(),
889        )
890    }
891    fn try_from_value(value: Value) -> Result<Self>
892    where
893        Self: Sized,
894    {
895        let context = Arc::new(format!(
896            "Could not create a chrono::NaiveDate from {value:?}"
897        ));
898        let v = <time::Date as AsValue>::try_from_value(value).context(context.clone())?;
899        chrono::NaiveDate::from_ymd_opt(v.year(), month_to_number!(v.month()), v.day() as _)
900            .context(context)
901    }
902}
903
904#[cfg(feature = "chrono")]
905impl AsValue for chrono::NaiveTime {
906    fn as_empty_value() -> Value {
907        Value::Time(None)
908    }
909    fn as_value(self) -> Value {
910        Value::Time(
911            time::Time::from_hms_nano(
912                self.hour() as _,
913                self.minute() as _,
914                self.second() as _,
915                self.nanosecond() as _,
916            )
917            .inspect_err(|e| {
918                log::error!("Could not create a Value::Time from chrono::NaiveTime: {e:?}",)
919            })
920            .ok(),
921        )
922    }
923    fn try_from_value(value: Value) -> Result<Self>
924    where
925        Self: Sized,
926    {
927        let context = Arc::new(format!(
928            "Could not create a chrono::NaiveTime from {value:?}"
929        ));
930        let v = <time::Time as AsValue>::try_from_value(value).context(context.clone())?;
931        Self::from_hms_nano_opt(
932            v.hour() as _,
933            v.minute() as _,
934            v.second() as _,
935            v.nanosecond() as _,
936        )
937        .context(context)
938    }
939}
940
941#[cfg(feature = "chrono")]
942impl AsValue for chrono::NaiveDateTime {
943    fn as_empty_value() -> Value {
944        Value::Timestamp(None)
945    }
946    fn as_value(self) -> Value {
947        Value::Timestamp(
948            'value: {
949                let Ok(date) = AsValue::try_from_value(self.date().as_value()) else {
950                    break 'value Err(Error::msg(
951                        "failed to convert the date part from chrono::NaiveDate to time::Date",
952                    ));
953                };
954                let Ok(time) = AsValue::try_from_value(self.time().as_value()) else {
955                    break 'value Err(Error::msg(
956                        "failed to convert the time part from chrono::NaiveTime to time::Time",
957                    ));
958                };
959                Ok(time::PrimitiveDateTime::new(date, time))
960            }
961            .inspect_err(|e| {
962                log::error!(
963                    "Could not create a Value::Timestamp from chrono::NaiveDateTime: {e:?}",
964                );
965            })
966            .ok(),
967        )
968    }
969    fn try_from_value(value: Value) -> Result<Self>
970    where
971        Self: Sized,
972    {
973        let context = Arc::new(format!(
974            "Could not create a chrono::NaiveDateTime from {value:?}"
975        ));
976        let v =
977            <time::PrimitiveDateTime as AsValue>::try_from_value(value).context(context.clone())?;
978        let date = AsValue::try_from_value(v.date().as_value()).context(context.clone())?;
979        let time = AsValue::try_from_value(v.time().as_value()).context(context.clone())?;
980        Ok(Self::new(date, time))
981    }
982}
983
984#[cfg(feature = "chrono")]
985impl AsValue for chrono::DateTime<chrono::FixedOffset> {
986    fn as_empty_value() -> Value {
987        Value::TimestampWithTimezone(None)
988    }
989    fn as_value(self) -> Value {
990        Value::TimestampWithTimezone(
991            'value: {
992                use chrono::Offset;
993                let Ok(date) = AsValue::try_from_value(self.date_naive().as_value()) else {
994                    break 'value Err(Error::msg(
995                        "failed to convert the date part from chrono::NaiveDate to time::Date",
996                    ));
997                };
998                let Ok(time) = AsValue::try_from_value(self.time().as_value()) else {
999                    break 'value Err(Error::msg(
1000                        "failed to convert the time part from chrono::NaiveTime to time::Time",
1001                    ));
1002                };
1003                let Ok(offset) =
1004                    time::UtcOffset::from_whole_seconds(self.offset().fix().local_minus_utc())
1005                else {
1006                    break 'value Err(Error::msg("failed to convert the offset part from"));
1007                };
1008                Ok(time::OffsetDateTime::new_in_offset(date, time, offset))
1009            }
1010            .inspect_err(|e| {
1011                log::error!(
1012                    "Could not create a Value::Timestamp from chrono::NaiveDateTime: {e:?}",
1013                );
1014            })
1015            .ok(),
1016        )
1017    }
1018    fn try_from_value(value: Value) -> Result<Self>
1019    where
1020        Self: Sized,
1021    {
1022        let context = Arc::new(format!(
1023            "Could not create a chrono::DateTime from {value:?}"
1024        ));
1025        let v =
1026            <time::OffsetDateTime as AsValue>::try_from_value(value).context(context.clone())?;
1027        let date = AsValue::try_from_value(v.date().as_value()).context(context.clone())?;
1028        let time = AsValue::try_from_value(v.time().as_value()).context(context.clone())?;
1029        let date_time = chrono::NaiveDateTime::new(date, time);
1030        let offset =
1031            chrono::FixedOffset::east_opt(v.offset().whole_seconds()).context(context.clone())?;
1032        Ok(Self::from_naive_utc_and_offset(date_time, offset))
1033    }
1034}
1035
1036#[cfg(feature = "chrono")]
1037impl AsValue for chrono::DateTime<chrono::Utc> {
1038    fn as_empty_value() -> Value {
1039        Value::TimestampWithTimezone(None)
1040    }
1041    fn as_value(self) -> Value {
1042        let odt = time::OffsetDateTime::from_unix_timestamp_nanos(
1043            self.timestamp_nanos_opt().unwrap() as i128,
1044        )
1045        .unwrap();
1046        Value::TimestampWithTimezone(Some(odt))
1047    }
1048    fn try_from_value(value: Value) -> Result<Self> {
1049        let odt = <time::OffsetDateTime as AsValue>::try_from_value(value)?;
1050        let utc_odt = odt.to_offset(time::UtcOffset::UTC);
1051        let secs = utc_odt.unix_timestamp();
1052        let nanos = utc_odt.nanosecond();
1053        Self::from_timestamp(secs, nanos)
1054            .ok_or_else(|| Error::msg("Timestamp out of range for chrono::DateTime<Utc>"))
1055    }
1056}
1057
1058impl AsValue for Decimal {
1059    fn as_empty_value() -> Value {
1060        Value::Decimal(None, 0, 0)
1061    }
1062    fn as_value(self) -> Value {
1063        Value::Decimal(Some(self), 0, self.scale() as _)
1064    }
1065    fn try_from_value(value: Value) -> Result<Self> {
1066        match value {
1067            Value::Decimal(Some(v), ..) => Ok(v),
1068            Value::Int8(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1069            Value::Int16(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1070            Value::Int32(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1071            Value::Int64(Some(v), ..) => Ok(Decimal::new(v, 0)),
1072            Value::UInt8(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1073            Value::UInt16(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1074            Value::UInt32(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1075            Value::UInt64(Some(v), ..) => Ok(Decimal::new(v as i64, 0)),
1076            Value::Float32(Some(v), ..) => Ok(Decimal::from_f32(v)
1077                .ok_or(Error::msg(format!("Cannot convert {value:?} to Decimal")))?),
1078            Value::Float64(Some(v), ..) => Ok(Decimal::from_f64(v)
1079                .ok_or(Error::msg(format!("Cannot convert {value:?} to Decimal")))?),
1080            Value::Json(Some(serde_json::Value::Number(v)), ..) => {
1081                if let Some(v) = v.as_f64()
1082                    && let Some(v) = Decimal::from_f64(v)
1083                {
1084                    return Ok(v);
1085                }
1086                Err(Error::msg(format!(
1087                    "Value {v} from json number is out of range for Decimal",
1088                )))
1089            }
1090            Value::Unknown(Some(v), ..) => Self::parse(&v),
1091            Value::Varchar(Some(v)) => Self::parse(&v),
1092            _ => Err(Error::msg(format!("Cannot convert {value:?} to Decimal"))),
1093        }
1094    }
1095    fn parse(input: impl AsRef<str>) -> Result<Self> {
1096        let input = input.as_ref();
1097        Ok(input.parse::<Decimal>().with_context(|| {
1098            Error::msg(format!(
1099                "Cannot parse a decimal value from `{}`",
1100                truncate_long!(input)
1101            ))
1102        })?)
1103    }
1104}
1105
1106impl<const W: u8, const S: u8> AsValue for FixedDecimal<W, S> {
1107    fn as_empty_value() -> Value {
1108        Decimal::as_empty_value()
1109    }
1110    fn as_value(self) -> Value {
1111        Value::Decimal(Some(self.0), W, self.0.scale() as _)
1112    }
1113    fn try_from_value(value: Value) -> Result<Self>
1114    where
1115        Self: Sized,
1116    {
1117        Ok(Self(Decimal::try_from_value(value)?))
1118    }
1119    fn parse(input: impl AsRef<str>) -> Result<Self> {
1120        <Decimal as AsValue>::parse(input).map(Into::into)
1121    }
1122}
1123
1124impl<T: AsValue, const N: usize> AsValue for [T; N] {
1125    fn as_empty_value() -> Value {
1126        Value::Array(None, Box::new(T::as_empty_value()), N as u32)
1127    }
1128    fn as_value(self) -> Value {
1129        Value::Array(
1130            Some(self.into_iter().map(AsValue::as_value).collect()),
1131            Box::new(T::as_empty_value()),
1132            N as u32,
1133        )
1134    }
1135    fn try_from_value(value: Value) -> Result<Self> {
1136        fn convert_iter<T: AsValue, const N: usize>(
1137            iter: impl IntoIterator<Item: AsValue>,
1138        ) -> Result<[T; N]> {
1139            iter.into_iter()
1140                .map(|v| T::try_from_value(v.as_value()))
1141                .collect::<Result<Vec<_>>>()?
1142                .try_into()
1143                .map_err(|v: Vec<T>| {
1144                    Error::msg(format!(
1145                        "Expected array of length {N}, got {} elements ({})",
1146                        v.len(),
1147                        any::type_name::<[T; N]>()
1148                    ))
1149                })
1150        }
1151        match value {
1152            Value::Varchar(Some(v), ..)
1153                if matches!(T::as_empty_value(), Value::Char(..)) && v.len() == N =>
1154            {
1155                convert_iter(v.chars())
1156            }
1157            Value::List(Some(v), ..) if v.len() == N => convert_iter(v.into_iter()),
1158            Value::Array(Some(v), ..) if v.len() == N => convert_iter(v.into_iter()),
1159            Value::Json(Some(serde_json::Value::Array(v))) if v.len() == N => {
1160                convert_iter(v.into_iter())
1161            }
1162            Value::Unknown(Some(v)) => <Self as AsValue>::parse(v),
1163            _ => Err(Error::msg(format!(
1164                "Cannot convert {value:?} to array {}",
1165                any::type_name::<Self>()
1166            ))),
1167        }
1168    }
1169}
1170
1171macro_rules! impl_as_value {
1172    ($source:ident) => {
1173        impl<T: AsValue> AsValue for $source<T> {
1174            fn as_empty_value() -> Value {
1175                Value::List(None, Box::new(T::as_empty_value()))
1176            }
1177            fn as_value(self) -> Value {
1178                Value::List(
1179                    Some(self.into_iter().map(AsValue::as_value).collect()),
1180                    Box::new(T::as_empty_value()),
1181                )
1182            }
1183            fn try_from_value(value: Value) -> Result<Self> {
1184                match value {
1185                    Value::List(None, ..) => Ok(Default::default()),
1186                    Value::List(Some(v), ..) => Ok(v
1187                        .into_iter()
1188                        .map(|v| Ok::<_, Error>(<T as AsValue>::try_from_value(v)?))
1189                        .collect::<Result<_>>()?),
1190                    Value::Array(Some(v), ..) => Ok(v
1191                        .into_iter()
1192                        .map(|v| Ok::<_, Error>(<T as AsValue>::try_from_value(v)?))
1193                        .collect::<Result<_>>()?),
1194                    Value::Json(Some(serde_json::Value::Array(v)), ..) => Ok(v
1195                        .into_iter()
1196                        .map(|v| Ok::<_, Error>(<T as AsValue>::try_from_value(v.as_value())?))
1197                        .collect::<Result<_>>()?),
1198                    _ => Err(Error::msg(format!(
1199                        "Cannot convert {value:?} to {}",
1200                        any::type_name::<Self>(),
1201                    ))),
1202                }
1203            }
1204        }
1205    };
1206}
1207impl_as_value!(Vec);
1208impl_as_value!(VecDeque);
1209impl_as_value!(LinkedList);
1210
1211macro_rules! impl_as_value {
1212    ($source:ident, $($key_trait:ident),+) => {
1213        impl<K: AsValue $(+ $key_trait)+, V: AsValue> AsValue for $source<K, V> {
1214            fn as_empty_value() -> Value {
1215                Value::Map(None, K::as_empty_value().into(), V::as_empty_value().into())
1216            }
1217            fn as_value(self) -> Value {
1218                Value::Map(
1219                    Some(
1220                        self.into_iter()
1221                            .map(|(k, v)| (k.as_value(), v.as_value()))
1222                            .collect(),
1223                    ),
1224                    K::as_empty_value().into(),
1225                    V::as_empty_value().into(),
1226                )
1227            }
1228            fn try_from_value(value: Value) -> Result<Self> {
1229                match value {
1230                    Value::Map(None, ..) => Ok(Default::default()),
1231                    Value::Map(Some(v), ..) => {
1232                        Ok(v.into_iter()
1233                            .map(|(k, v)| {
1234                                Ok((
1235                                    <K as AsValue>::try_from_value(k)?,
1236                                    <V as AsValue>::try_from_value(v)?,
1237                                ))
1238                            })
1239                            .collect::<Result<_>>()?)
1240                    }
1241                    Value::Json(Some(serde_json::Value::Object(v)), ..) => {
1242                        Ok(v.into_iter()
1243                            .map(|(k, v)| {
1244                                Ok((
1245                                    <K as AsValue>::try_from_value(serde_json::Value::String(k).as_value())?,
1246                                    <V as AsValue>::try_from_value(v.as_value())?,
1247                                ))
1248                            })
1249                            .collect::<Result<_>>()?)
1250                    }
1251                    _=> {
1252                        Err(Error::msg(format!(
1253                            "Cannot convert {value:?} to {}",
1254                            any::type_name::<Self>(),
1255                        )))
1256                    }
1257                }
1258            }
1259        }
1260    }
1261}
1262impl_as_value!(BTreeMap, Ord);
1263impl_as_value!(HashMap, Eq, Hash);
1264
1265impl AsValue for &'static str {
1266    fn as_empty_value() -> Value {
1267        Value::Varchar(None)
1268    }
1269    fn as_value(self) -> Value {
1270        Value::Varchar(Some(self.into()))
1271    }
1272    fn try_from_value(value: Value) -> Result<Self>
1273    where
1274        Self: Sized,
1275    {
1276        let Value::Varchar(Some(Cow::Borrowed(v))) = value.try_as(&Value::Varchar(None))? else {
1277            return Err(Error::msg(format!(
1278                "Cannot assign a `&'static str` with data fetched from the database. Please consider `Cow<'static, str>` instead, can still use `&'static str` for data insertion purpose.",
1279            )));
1280        };
1281        Ok(v)
1282    }
1283}
1284
1285impl AsValue for Cow<'static, str> {
1286    fn as_empty_value() -> Value {
1287        Value::Varchar(None)
1288    }
1289    fn as_value(self) -> Value {
1290        Value::Varchar(Some(self.into()))
1291    }
1292    fn try_from_value(value: Value) -> Result<Self>
1293    where
1294        Self: Sized,
1295    {
1296        String::try_from_value(value).map(Into::into)
1297    }
1298    fn parse(input: impl AsRef<str>) -> Result<Self>
1299    where
1300        Self: Sized,
1301    {
1302        <String as AsValue>::parse(input).map(Into::into)
1303    }
1304}
1305
1306impl<T: AsValue> AsValue for Passive<T> {
1307    fn as_empty_value() -> Value {
1308        T::as_empty_value()
1309    }
1310    fn as_value(self) -> Value {
1311        match self {
1312            Passive::Set(v) => v.as_value(),
1313            Passive::NotSet => T::as_empty_value(),
1314        }
1315    }
1316    fn try_from_value(value: Value) -> Result<Self> {
1317        Ok(Passive::Set(<T as AsValue>::try_from_value(value)?))
1318    }
1319}
1320
1321impl<T: AsValue> AsValue for Option<T> {
1322    fn as_empty_value() -> Value {
1323        T::as_empty_value()
1324    }
1325    fn as_value(self) -> Value {
1326        match self {
1327            Some(v) => v.as_value(),
1328            None => T::as_empty_value(),
1329        }
1330    }
1331    fn try_from_value(value: Value) -> Result<Self> {
1332        Ok(if value.is_null() {
1333            None
1334        } else {
1335            Some(<T as AsValue>::try_from_value(value)?)
1336        })
1337    }
1338    fn parse(input: impl AsRef<str>) -> Result<Self>
1339    where
1340        Self: Sized,
1341    {
1342        let mut value = input.as_ref();
1343        let result = consume_while(&mut value, |v| v.is_alphanumeric() || *v == '_');
1344        if result.eq_ignore_ascii_case("null") {
1345            return Ok(None);
1346        };
1347        T::parse(input).map(Some)
1348    }
1349}
1350
1351// TODO: Use the macro below once box_into_inner is stabilized
1352impl<T: AsValue> AsValue for Box<T> {
1353    fn as_empty_value() -> Value {
1354        T::as_empty_value()
1355    }
1356    fn as_value(self) -> Value {
1357        (*self).as_value()
1358    }
1359    fn try_from_value(value: Value) -> Result<Self> {
1360        Ok(Self::new(<T as AsValue>::try_from_value(value)?))
1361    }
1362    fn parse(input: impl AsRef<str>) -> Result<Self>
1363    where
1364        Self: Sized,
1365    {
1366        T::parse(input).map(Self::new)
1367    }
1368}
1369
1370macro_rules! impl_as_value {
1371    ($source:ident) => {
1372        impl<T: AsValue + ToOwned<Owned = impl AsValue>> AsValue for $source<T> {
1373            fn as_empty_value() -> Value {
1374                T::as_empty_value()
1375            }
1376            fn as_value(self) -> Value {
1377                $source::<T>::into_inner(self).as_value()
1378            }
1379            fn try_from_value(value: Value) -> Result<Self> {
1380                Ok($source::new(<T as AsValue>::try_from_value(value)?))
1381            }
1382        }
1383    };
1384}
1385// impl_as_value!(Box);
1386impl_as_value!(Cell);
1387impl_as_value!(RefCell);
1388
1389impl<T: AsValue> AsValue for RwLock<T> {
1390    fn as_empty_value() -> Value {
1391        T::as_empty_value()
1392    }
1393    fn as_value(self) -> Value {
1394        self.into_inner()
1395            .expect("Error occurred while trying to take the content of the RwLock")
1396            .as_value()
1397    }
1398    fn try_from_value(value: Value) -> Result<Self> {
1399        Ok(RwLock::new(<T as AsValue>::try_from_value(value)?))
1400    }
1401    fn parse(input: impl AsRef<str>) -> Result<Self>
1402    where
1403        Self: Sized,
1404    {
1405        T::parse(input).map(Self::new)
1406    }
1407}
1408
1409macro_rules! impl_as_value {
1410    ($source:ident) => {
1411        impl<T: AsValue + ToOwned<Owned = impl AsValue>> AsValue for $source<T> {
1412            fn as_empty_value() -> Value {
1413                T::as_empty_value()
1414            }
1415            fn as_value(self) -> Value {
1416                $source::try_unwrap(self)
1417                    .map(|v| v.as_value())
1418                    .unwrap_or_else(|v| v.as_ref().to_owned().as_value())
1419            }
1420            fn try_from_value(value: Value) -> Result<Self> {
1421                Ok($source::new(<T as AsValue>::try_from_value(value)?))
1422            }
1423            fn parse(input: impl AsRef<str>) -> Result<Self>
1424            where
1425                Self: Sized,
1426            {
1427                T::parse(input).map(Self::new)
1428            }
1429        }
1430    };
1431}
1432impl_as_value!(Arc);
1433impl_as_value!(Rc);
1434
1435impl AsValue for serde_json::Value {
1436    fn as_empty_value() -> Value {
1437        Value::Json(None)
1438    }
1439    fn as_value(self) -> Value {
1440        Value::Json(Some(self))
1441    }
1442    fn try_from_value(value: Value) -> Result<Self>
1443    where
1444        Self: Sized,
1445    {
1446        Ok(if let Value::Json(v) = value {
1447            match v {
1448                Some(v) => v,
1449                None => Self::Null,
1450            }
1451        } else {
1452            return Err(Error::msg(
1453                "Cannot convert non json tank::Value to serde_json::Value",
1454            ));
1455        })
1456    }
1457}