scylla_cql/deserialize/
value.rs

1//! Provides types for dealing with CQL value deserialization.
2
3use std::{
4    borrow::Cow,
5    collections::{BTreeMap, BTreeSet, HashMap, HashSet},
6    hash::{BuildHasher, Hash},
7    net::IpAddr,
8    sync::Arc,
9};
10
11use bytes::Bytes;
12use uuid::Uuid;
13
14use std::fmt::Display;
15
16use thiserror::Error;
17
18use super::{DeserializationError, FrameSlice, TypeCheckError, make_error_replace_rust_name};
19use crate::frame::frame_errors::LowLevelDeserializationError;
20use crate::frame::response::result::CollectionType;
21use crate::frame::response::result::UserDefinedType;
22use crate::frame::response::result::{ColumnType, NativeType};
23use crate::frame::types;
24use crate::value::CqlVarintBorrowed;
25use crate::value::{
26    Counter, CqlDate, CqlDecimal, CqlDecimalBorrowed, CqlDuration, CqlTime, CqlTimestamp,
27    CqlTimeuuid, CqlValue, CqlVarint, deser_cql_value,
28};
29
30/// A type that can be deserialized from a column value inside a row that was
31/// returned from a query.
32///
33/// For tips on how to write a custom implementation of this trait, see the
34/// documentation of the parent module.
35///
36/// The crate also provides a derive macro which allows to automatically
37/// implement the trait for a custom type. For more details on what the macro
38/// is capable of, see its documentation.
39pub trait DeserializeValue<'frame, 'metadata>
40where
41    Self: Sized,
42{
43    /// Checks that the column type matches what this type expects.
44    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError>;
45
46    /// Deserialize a column value from given serialized representation.
47    ///
48    /// This function can assume that the driver called `type_check` to verify
49    /// the column's type. Note that `deserialize` is not an unsafe function,
50    /// so it should not use the assumption about `type_check` being called
51    /// as an excuse to run `unsafe` code.
52    fn deserialize(
53        typ: &'metadata ColumnType<'metadata>,
54        v: Option<FrameSlice<'frame>>,
55    ) -> Result<Self, DeserializationError>;
56}
57
58impl<'frame, 'metadata> DeserializeValue<'frame, 'metadata> for CqlValue {
59    fn type_check(_typ: &ColumnType) -> Result<(), TypeCheckError> {
60        // CqlValue accepts all possible CQL types
61        Ok(())
62    }
63
64    fn deserialize(
65        typ: &'metadata ColumnType<'metadata>,
66        v: Option<FrameSlice<'frame>>,
67    ) -> Result<Self, DeserializationError> {
68        let mut val = ensure_not_null_slice::<Self>(typ, v)?;
69        let cql = deser_cql_value(typ, &mut val).map_err(deser_error_replace_rust_name::<Self>)?;
70        Ok(cql)
71    }
72}
73
74// Option represents nullability of CQL values:
75// None corresponds to null,
76// Some(val) to non-null values.
77impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata> for Option<T>
78where
79    T: DeserializeValue<'frame, 'metadata>,
80{
81    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
82        T::type_check(typ).map_err(typck_error_replace_rust_name::<Self>)
83    }
84
85    fn deserialize(
86        typ: &'metadata ColumnType<'metadata>,
87        v: Option<FrameSlice<'frame>>,
88    ) -> Result<Self, DeserializationError> {
89        v.map(|_| T::deserialize(typ, v))
90            .transpose()
91            .map_err(deser_error_replace_rust_name::<Self>)
92    }
93}
94
95/// Values that may be empty or not.
96///
97/// In CQL, some types can have a special value of "empty", represented as
98/// a serialized value of length 0. An example of this are integral types:
99/// the "int" type can actually hold 2^32 + 1 possible values because of this
100/// quirk. Note that this is distinct from being NULL.
101///
102/// Rust types that cannot represent an empty value (e.g. i32) should implement
103/// this trait in order to be deserialized as [MaybeEmpty].
104pub trait Emptiable {}
105
106/// A value that may be empty or not.
107///
108/// `MaybeEmpty` was introduced to help support the quirk described in [Emptiable]
109/// for Rust types which can't represent the empty, additional value.
110#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Clone, Copy)]
111pub enum MaybeEmpty<T: Emptiable> {
112    Empty,
113    Value(T),
114}
115
116impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata> for MaybeEmpty<T>
117where
118    T: DeserializeValue<'frame, 'metadata> + Emptiable,
119{
120    #[inline]
121    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
122        <T as DeserializeValue<'frame, 'metadata>>::type_check(typ)
123            .map_err(typck_error_replace_rust_name::<Self>)
124    }
125
126    fn deserialize(
127        typ: &'metadata ColumnType<'metadata>,
128        v: Option<FrameSlice<'frame>>,
129    ) -> Result<Self, DeserializationError> {
130        let val = ensure_not_null_slice::<Self>(typ, v)?;
131        if val.is_empty() {
132            Ok(MaybeEmpty::Empty)
133        } else {
134            let v = <T as DeserializeValue<'frame, 'metadata>>::deserialize(typ, v)
135                .map_err(deser_error_replace_rust_name::<Self>)?;
136            Ok(MaybeEmpty::Value(v))
137        }
138    }
139}
140
141macro_rules! impl_strict_type {
142    ($t:ty, [$($cql:ident)|+], $conv:expr $(, $l:lifetime)?) => {
143        impl<$($l,)? 'frame, 'metadata> DeserializeValue<'frame, 'metadata> for $t
144        where
145            $('frame: $l)?
146        {
147            fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
148                // TODO: Format the CQL type names in the same notation
149                // that ScyllaDB/Cassandra uses internally and include them
150                // in such form in the error message
151                exact_type_check!(typ, $($cql),*);
152                Ok(())
153            }
154
155            fn deserialize(
156                typ: &'metadata ColumnType<'metadata>,
157                v: Option<FrameSlice<'frame>>,
158            ) -> Result<Self, DeserializationError> {
159                $conv(typ, v)
160            }
161        }
162    };
163
164    // Convenience pattern for omitting brackets if type-checking as single types.
165    ($t:ty, $cql:ident, $conv:expr $(, $l:lifetime)?) => {
166        impl_strict_type!($t, [$cql], $conv $(, $l)*);
167    };
168}
169
170macro_rules! impl_emptiable_strict_type {
171    ($t:ty, [$($cql:ident)|+], $conv:expr $(, $l:lifetime)?) => {
172        impl<$($l,)?> Emptiable for $t {}
173
174        impl_strict_type!($t, [$($cql)|*], $conv $(, $l)*);
175    };
176
177    // Convenience pattern for omitting brackets if type-checking as single types.
178    ($t:ty, $cql:ident, $conv:expr $(, $l:lifetime)?) => {
179        impl_emptiable_strict_type!($t, [$cql], $conv $(, $l)*);
180    };
181
182}
183
184// fixed numeric types
185
186macro_rules! impl_fixed_numeric_type {
187    ($t:ty, [$($cql:ident)|+]) => {
188        impl_emptiable_strict_type!(
189            $t,
190            [$($cql)|*],
191            |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
192                const SIZE: usize = std::mem::size_of::<$t>();
193                let val = ensure_not_null_slice::<Self>(typ, v)?;
194                let arr = ensure_exact_length::<Self, SIZE>(typ, val)?;
195                Ok(<$t>::from_be_bytes(*arr))
196            }
197        );
198    };
199
200    // Convenience pattern for omitting brackets if type-checking as single types.
201    ($t:ty, $cql:ident) => {
202        impl_fixed_numeric_type!($t, [$cql]);
203    };
204}
205
206impl_emptiable_strict_type!(
207    bool,
208    Boolean,
209    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
210        let val = ensure_not_null_slice::<Self>(typ, v)?;
211        let arr = ensure_exact_length::<Self, 1>(typ, val)?;
212        Ok(arr[0] != 0x00)
213    }
214);
215
216impl_fixed_numeric_type!(i8, TinyInt);
217impl_fixed_numeric_type!(i16, SmallInt);
218impl_fixed_numeric_type!(i32, Int);
219impl_fixed_numeric_type!(i64, BigInt);
220impl_fixed_numeric_type!(f32, Float);
221impl_fixed_numeric_type!(f64, Double);
222
223// other numeric types
224
225impl_emptiable_strict_type!(
226    CqlVarint,
227    Varint,
228    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
229        let val = ensure_not_null_slice::<Self>(typ, v)?;
230        Ok(CqlVarint::from_signed_bytes_be_slice(val))
231    }
232);
233
234impl_emptiable_strict_type!(
235    CqlVarintBorrowed<'b>,
236    Varint,
237    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
238        let val = ensure_not_null_slice::<Self>(typ, v)?;
239        Ok(CqlVarintBorrowed::from_signed_bytes_be_slice(val))
240    },
241    'b
242);
243
244#[cfg(feature = "num-bigint-03")]
245impl_emptiable_strict_type!(
246    num_bigint_03::BigInt,
247    Varint,
248    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
249        let val = ensure_not_null_slice::<Self>(typ, v)?;
250        Ok(num_bigint_03::BigInt::from_signed_bytes_be(val))
251    }
252);
253
254#[cfg(feature = "num-bigint-04")]
255impl_emptiable_strict_type!(
256    num_bigint_04::BigInt,
257    Varint,
258    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
259        let val = ensure_not_null_slice::<Self>(typ, v)?;
260        Ok(num_bigint_04::BigInt::from_signed_bytes_be(val))
261    }
262);
263
264impl_emptiable_strict_type!(
265    CqlDecimal,
266    Decimal,
267    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
268        let mut val = ensure_not_null_slice::<Self>(typ, v)?;
269        let scale = types::read_int(&mut val).map_err(|err| {
270            mk_deser_err::<Self>(
271                typ,
272                BuiltinDeserializationErrorKind::BadDecimalScale(err.into()),
273            )
274        })?;
275        Ok(CqlDecimal::from_signed_be_bytes_slice_and_exponent(
276            val, scale,
277        ))
278    }
279);
280
281impl_emptiable_strict_type!(
282    CqlDecimalBorrowed<'b>,
283    Decimal,
284    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
285        let mut val = ensure_not_null_slice::<Self>(typ, v)?;
286        let scale = types::read_int(&mut val).map_err(|err| {
287            mk_deser_err::<Self>(
288                typ,
289                BuiltinDeserializationErrorKind::BadDecimalScale(err.into()),
290            )
291        })?;
292        Ok(CqlDecimalBorrowed::from_signed_be_bytes_slice_and_exponent(
293            val, scale,
294        ))
295    },
296    'b
297);
298
299#[cfg(feature = "bigdecimal-04")]
300impl_emptiable_strict_type!(
301    bigdecimal_04::BigDecimal,
302    Decimal,
303    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
304        let mut val = ensure_not_null_slice::<Self>(typ, v)?;
305        let scale = types::read_int(&mut val).map_err(|err| {
306            mk_deser_err::<Self>(
307                typ,
308                BuiltinDeserializationErrorKind::BadDecimalScale(err.into()),
309            )
310        })? as i64;
311        let int_value = bigdecimal_04::num_bigint::BigInt::from_signed_bytes_be(val);
312        Ok(bigdecimal_04::BigDecimal::from((int_value, scale)))
313    }
314);
315
316// blob
317
318impl_strict_type!(
319    &'a [u8],
320    Blob,
321    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
322        let val = ensure_not_null_slice::<Self>(typ, v)?;
323        Ok(val)
324    },
325    'a
326);
327impl_strict_type!(
328    Vec<u8>,
329    Blob,
330    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
331        let val = ensure_not_null_slice::<Self>(typ, v)?;
332        Ok(val.to_vec())
333    }
334);
335impl_strict_type!(
336    Bytes,
337    Blob,
338    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
339        let val = ensure_not_null_owned::<Self>(typ, v)?;
340        Ok(val)
341    }
342);
343
344// string
345
346macro_rules! impl_string_type {
347    ($t:ty, $conv:expr $(, $l:lifetime)?) => {
348        impl_strict_type!(
349            $t,
350            [Ascii | Text],
351            $conv
352            $(, $l)?
353        );
354    }
355}
356
357fn check_ascii<T>(typ: &ColumnType, s: &[u8]) -> Result<(), DeserializationError> {
358    if matches!(typ, ColumnType::Native(NativeType::Ascii)) && !s.is_ascii() {
359        return Err(mk_deser_err::<T>(
360            typ,
361            BuiltinDeserializationErrorKind::ExpectedAscii,
362        ));
363    }
364    Ok(())
365}
366
367impl_string_type!(
368    &'a str,
369    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
370        let val = ensure_not_null_slice::<Self>(typ, v)?;
371        check_ascii::<&str>(typ, val)?;
372        let s = std::str::from_utf8(val).map_err(|err| {
373            mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::InvalidUtf8(err))
374        })?;
375        Ok(s)
376    },
377    'a
378);
379impl_string_type!(
380    String,
381    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
382        let val = ensure_not_null_slice::<Self>(typ, v)?;
383        check_ascii::<String>(typ, val)?;
384        let s = std::str::from_utf8(val).map_err(|err| {
385            mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::InvalidUtf8(err))
386        })?;
387        Ok(s.to_string())
388    }
389);
390
391// TODO: Consider support for deserialization of string::String<Bytes>
392
393// counter
394
395impl_strict_type!(
396    Counter,
397    Counter,
398    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
399        let val = ensure_not_null_slice::<Self>(typ, v)?;
400        let arr = ensure_exact_length::<Self, 8>(typ, val)?;
401        let counter = i64::from_be_bytes(*arr);
402        Ok(Counter(counter))
403    }
404);
405
406// date and time types
407
408// duration
409impl_strict_type!(
410    CqlDuration,
411    Duration,
412    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
413        let mut val = ensure_not_null_slice::<Self>(typ, v)?;
414
415        macro_rules! mk_err {
416            ($err: expr) => {
417                mk_deser_err::<Self>(typ, $err)
418            };
419        }
420
421        let months_i64 = types::vint_decode(&mut val).map_err(|err| {
422            mk_err!(BuiltinDeserializationErrorKind::BadDate {
423                date_field: "months",
424                err: err.into()
425            })
426        })?;
427        let months = i32::try_from(months_i64)
428            .map_err(|_| mk_err!(BuiltinDeserializationErrorKind::ValueOverflow))?;
429
430        let days_i64 = types::vint_decode(&mut val).map_err(|err| {
431            mk_err!(BuiltinDeserializationErrorKind::BadDate {
432                date_field: "days",
433                err: err.into()
434            })
435        })?;
436        let days = i32::try_from(days_i64)
437            .map_err(|_| mk_err!(BuiltinDeserializationErrorKind::ValueOverflow))?;
438
439        let nanoseconds = types::vint_decode(&mut val).map_err(|err| {
440            mk_err!(BuiltinDeserializationErrorKind::BadDate {
441                date_field: "nanoseconds",
442                err: err.into()
443            })
444        })?;
445
446        Ok(CqlDuration {
447            months,
448            days,
449            nanoseconds,
450        })
451    }
452);
453
454impl_emptiable_strict_type!(
455    CqlDate,
456    Date,
457    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
458        let val = ensure_not_null_slice::<Self>(typ, v)?;
459        let arr = ensure_exact_length::<Self, 4>(typ, val)?;
460        let days = u32::from_be_bytes(*arr);
461        Ok(CqlDate(days))
462    }
463);
464
465#[cfg(any(feature = "chrono-04", feature = "time-03"))]
466fn get_days_since_epoch_from_date_column<T>(
467    typ: &ColumnType,
468    v: Option<FrameSlice<'_>>,
469) -> Result<i64, DeserializationError> {
470    let val = ensure_not_null_slice::<T>(typ, v)?;
471    let arr = ensure_exact_length::<T, 4>(typ, val)?;
472    let days = u32::from_be_bytes(*arr);
473    let days_since_epoch = days as i64 - (1i64 << 31);
474    Ok(days_since_epoch)
475}
476
477#[cfg(feature = "chrono-04")]
478impl_emptiable_strict_type!(chrono_04::NaiveDate, Date, |typ: &'metadata ColumnType<
479    'metadata,
480>,
481                                                         v: Option<
482    FrameSlice<'frame>,
483>| {
484    let fail = || mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::ValueOverflow);
485    let days_since_epoch =
486        chrono_04::Duration::try_days(get_days_since_epoch_from_date_column::<Self>(typ, v)?)
487            .ok_or_else(fail)?;
488    chrono_04::NaiveDate::from_ymd_opt(1970, 1, 1)
489        .unwrap()
490        .checked_add_signed(days_since_epoch)
491        .ok_or_else(fail)
492});
493
494#[cfg(feature = "time-03")]
495impl_emptiable_strict_type!(
496    time_03::Date,
497    Date,
498    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
499        let days_since_epoch =
500            time_03::Duration::days(get_days_since_epoch_from_date_column::<Self>(typ, v)?);
501        time_03::Date::from_calendar_date(1970, time_03::Month::January, 1)
502            .unwrap()
503            .checked_add(days_since_epoch)
504            .ok_or_else(|| {
505                mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::ValueOverflow)
506            })
507    }
508);
509
510fn get_nanos_from_time_column<T>(
511    typ: &ColumnType,
512    v: Option<FrameSlice<'_>>,
513) -> Result<i64, DeserializationError> {
514    let val = ensure_not_null_slice::<T>(typ, v)?;
515    let arr = ensure_exact_length::<T, 8>(typ, val)?;
516    let nanoseconds = i64::from_be_bytes(*arr);
517
518    // Valid values are in the range 0 to 86399999999999
519    if !(0..=86399999999999).contains(&nanoseconds) {
520        return Err(mk_deser_err::<T>(
521            typ,
522            BuiltinDeserializationErrorKind::ValueOverflow,
523        ));
524    }
525
526    Ok(nanoseconds)
527}
528
529impl_emptiable_strict_type!(
530    CqlTime,
531    Time,
532    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
533        let nanoseconds = get_nanos_from_time_column::<Self>(typ, v)?;
534
535        Ok(CqlTime(nanoseconds))
536    }
537);
538
539#[cfg(feature = "chrono-04")]
540impl_emptiable_strict_type!(chrono_04::NaiveTime, Time, |typ: &'metadata ColumnType<
541    'metadata,
542>,
543                                                         v: Option<
544    FrameSlice<'frame>,
545>| {
546    let nanoseconds = get_nanos_from_time_column::<chrono_04::NaiveTime>(typ, v)?;
547
548    let naive_time: chrono_04::NaiveTime = CqlTime(nanoseconds)
549        .try_into()
550        .map_err(|_| mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::ValueOverflow))?;
551    Ok(naive_time)
552});
553
554#[cfg(feature = "time-03")]
555impl_emptiable_strict_type!(
556    time_03::Time,
557    Time,
558    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
559        let nanoseconds = get_nanos_from_time_column::<time_03::Time>(typ, v)?;
560
561        let time: time_03::Time = CqlTime(nanoseconds).try_into().map_err(|_| {
562            mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::ValueOverflow)
563        })?;
564        Ok(time)
565    }
566);
567
568fn get_millis_from_timestamp_column<T>(
569    typ: &ColumnType,
570    v: Option<FrameSlice<'_>>,
571) -> Result<i64, DeserializationError> {
572    let val = ensure_not_null_slice::<T>(typ, v)?;
573    let arr = ensure_exact_length::<T, 8>(typ, val)?;
574    let millis = i64::from_be_bytes(*arr);
575
576    Ok(millis)
577}
578
579impl_emptiable_strict_type!(
580    CqlTimestamp,
581    Timestamp,
582    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
583        let millis = get_millis_from_timestamp_column::<Self>(typ, v)?;
584        Ok(CqlTimestamp(millis))
585    }
586);
587
588#[cfg(feature = "chrono-04")]
589impl_emptiable_strict_type!(
590    chrono_04::DateTime<chrono_04::Utc>,
591    Timestamp,
592    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
593        use chrono_04::TimeZone as _;
594
595        let millis = get_millis_from_timestamp_column::<Self>(typ, v)?;
596        match chrono_04::Utc.timestamp_millis_opt(millis) {
597            chrono_04::LocalResult::Single(datetime) => Ok(datetime),
598            _ => Err(mk_deser_err::<Self>(
599                typ,
600                BuiltinDeserializationErrorKind::ValueOverflow,
601            )),
602        }
603    }
604);
605
606#[cfg(feature = "time-03")]
607impl_emptiable_strict_type!(
608    time_03::OffsetDateTime,
609    Timestamp,
610    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
611        let millis = get_millis_from_timestamp_column::<Self>(typ, v)?;
612        time_03::OffsetDateTime::from_unix_timestamp_nanos(millis as i128 * 1_000_000)
613            .map_err(|_| mk_deser_err::<Self>(typ, BuiltinDeserializationErrorKind::ValueOverflow))
614    }
615);
616
617// inet
618
619impl_emptiable_strict_type!(
620    IpAddr,
621    Inet,
622    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
623        let val = ensure_not_null_slice::<Self>(typ, v)?;
624        if let Ok(ipv4) = <[u8; 4]>::try_from(val) {
625            Ok(IpAddr::from(ipv4))
626        } else if let Ok(ipv6) = <[u8; 16]>::try_from(val) {
627            Ok(IpAddr::from(ipv6))
628        } else {
629            Err(mk_deser_err::<Self>(
630                typ,
631                BuiltinDeserializationErrorKind::BadInetLength { got: val.len() },
632            ))
633        }
634    }
635);
636
637// uuid
638
639impl_emptiable_strict_type!(
640    Uuid,
641    Uuid,
642    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
643        let val = ensure_not_null_slice::<Self>(typ, v)?;
644        let arr = ensure_exact_length::<Self, 16>(typ, val)?;
645        let i = u128::from_be_bytes(*arr);
646        Ok(uuid::Uuid::from_u128(i))
647    }
648);
649
650impl_emptiable_strict_type!(
651    CqlTimeuuid,
652    Timeuuid,
653    |typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>| {
654        let val = ensure_not_null_slice::<Self>(typ, v)?;
655        let arr = ensure_exact_length::<Self, 16>(typ, val)?;
656        let i = u128::from_be_bytes(*arr);
657        Ok(CqlTimeuuid::from(uuid::Uuid::from_u128(i)))
658    }
659);
660
661// secrecy
662#[cfg(feature = "secrecy-08")]
663impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata> for secrecy_08::Secret<T>
664where
665    T: DeserializeValue<'frame, 'metadata> + secrecy_08::Zeroize,
666{
667    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
668        <T as DeserializeValue<'frame, 'metadata>>::type_check(typ)
669            .map_err(typck_error_replace_rust_name::<Self>)
670    }
671
672    fn deserialize(
673        typ: &'metadata ColumnType<'metadata>,
674        v: Option<FrameSlice<'frame>>,
675    ) -> Result<Self, DeserializationError> {
676        <T as DeserializeValue<'frame, 'metadata>>::deserialize(typ, v)
677            .map(secrecy_08::Secret::new)
678            .map_err(deser_error_replace_rust_name::<Self>)
679    }
680}
681
682// collections
683
684make_error_replace_rust_name!(
685    pub(crate),
686    typck_error_replace_rust_name,
687    TypeCheckError,
688    BuiltinTypeCheckError
689);
690
691make_error_replace_rust_name!(
692    pub,
693    deser_error_replace_rust_name,
694    DeserializationError,
695    BuiltinDeserializationError
696);
697
698// lists and sets
699
700/// An iterator over either a CQL set or list.
701#[derive(Debug, Clone)]
702pub struct ListlikeIterator<'frame, 'metadata, T> {
703    coll_typ: &'metadata ColumnType<'metadata>,
704    elem_typ: &'metadata ColumnType<'metadata>,
705    raw_iter: FixedLengthBytesSequenceIterator<'frame>,
706    phantom_data: std::marker::PhantomData<T>,
707}
708
709impl<'frame, 'metadata, T> ListlikeIterator<'frame, 'metadata, T> {
710    fn new(
711        coll_typ: &'metadata ColumnType<'metadata>,
712        elem_typ: &'metadata ColumnType<'metadata>,
713        count: usize,
714        slice: FrameSlice<'frame>,
715    ) -> Self {
716        Self {
717            coll_typ,
718            elem_typ,
719            raw_iter: FixedLengthBytesSequenceIterator::new(count, slice),
720            phantom_data: std::marker::PhantomData,
721        }
722    }
723
724    fn empty(
725        coll_typ: &'metadata ColumnType<'metadata>,
726        elem_typ: &'metadata ColumnType<'metadata>,
727    ) -> Self {
728        Self {
729            coll_typ,
730            elem_typ,
731            raw_iter: FixedLengthBytesSequenceIterator::empty(),
732            phantom_data: std::marker::PhantomData,
733        }
734    }
735}
736
737impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata>
738    for ListlikeIterator<'frame, 'metadata, T>
739where
740    T: DeserializeValue<'frame, 'metadata>,
741{
742    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
743        match typ {
744            ColumnType::Collection {
745                frozen: false,
746                typ: CollectionType::List(el_t),
747            }
748            | ColumnType::Collection {
749                frozen: false,
750                typ: CollectionType::Set(el_t),
751            } => <T as DeserializeValue<'frame, 'metadata>>::type_check(el_t).map_err(|err| {
752                mk_typck_err::<Self>(
753                    typ,
754                    SetOrListTypeCheckErrorKind::ElementTypeCheckFailed(err),
755                )
756            }),
757            _ => Err(mk_typck_err::<Self>(
758                typ,
759                BuiltinTypeCheckErrorKind::SetOrListError(
760                    SetOrListTypeCheckErrorKind::NotSetOrList,
761                ),
762            )),
763        }
764    }
765
766    fn deserialize(
767        typ: &'metadata ColumnType<'metadata>,
768        v: Option<FrameSlice<'frame>>,
769    ) -> Result<Self, DeserializationError> {
770        let elem_typ = match typ {
771            ColumnType::Collection {
772                frozen: false,
773                typ: CollectionType::List(elem_typ),
774            }
775            | ColumnType::Collection {
776                frozen: false,
777                typ: CollectionType::Set(elem_typ),
778            } => elem_typ,
779            _ => {
780                unreachable!("Typecheck should have prevented this scenario!")
781            }
782        };
783
784        let mut v = if let Some(v) = v {
785            v
786        } else {
787            return Ok(Self::empty(typ, elem_typ));
788        };
789
790        let count = types::read_int_length(v.as_slice_mut()).map_err(|err| {
791            mk_deser_err::<Self>(
792                typ,
793                SetOrListDeserializationErrorKind::LengthDeserializationFailed(
794                    DeserializationError::new(err),
795                ),
796            )
797        })?;
798
799        Ok(Self::new(typ, elem_typ, count, v))
800    }
801}
802
803impl<'frame, 'metadata, T> Iterator for ListlikeIterator<'frame, 'metadata, T>
804where
805    T: DeserializeValue<'frame, 'metadata>,
806{
807    type Item = Result<T, DeserializationError>;
808
809    fn next(&mut self) -> Option<Self::Item> {
810        let raw = self.raw_iter.next()?.map_err(|err| {
811            mk_deser_err::<Self>(
812                self.coll_typ,
813                BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
814            )
815        });
816        Some(raw.and_then(|raw| {
817            T::deserialize(self.elem_typ, raw).map_err(|err| {
818                mk_deser_err::<Self>(
819                    self.coll_typ,
820                    SetOrListDeserializationErrorKind::ElementDeserializationFailed(err),
821                )
822            })
823        }))
824    }
825
826    #[inline]
827    fn size_hint(&self) -> (usize, Option<usize>) {
828        self.raw_iter.size_hint()
829    }
830}
831
832impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata> for Vec<T>
833where
834    T: DeserializeValue<'frame, 'metadata>,
835{
836    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
837        // It makes sense for Set, List and Vector to deserialize to Vec.
838        match typ {
839            ColumnType::Collection {
840                typ: CollectionType::List(_) | CollectionType::Set(_),
841                ..
842            } => ListlikeIterator::<'frame, 'metadata, T>::type_check(typ)
843                .map_err(typck_error_replace_rust_name::<Self>),
844            ColumnType::Vector { .. } => VectorIterator::<'frame, 'metadata, T>::type_check(typ)
845                .map_err(typck_error_replace_rust_name::<Self>),
846            _ => Err(mk_typck_err::<Self>(
847                typ,
848                BuiltinTypeCheckErrorKind::NotDeserializableToVec,
849            )),
850        }
851    }
852
853    fn deserialize(
854        typ: &'metadata ColumnType<'metadata>,
855        v: Option<FrameSlice<'frame>>,
856    ) -> Result<Self, DeserializationError> {
857        match typ {
858            ColumnType::Collection {
859                typ: CollectionType::List(_) | CollectionType::Set(_),
860                ..
861            } => ListlikeIterator::<'frame, 'metadata, T>::deserialize(typ, v)
862                .and_then(|it| it.collect::<Result<_, DeserializationError>>())
863                .map_err(deser_error_replace_rust_name::<Self>),
864            ColumnType::Vector { .. } => {
865                VectorIterator::<'frame, 'metadata, T>::deserialize(typ, v)
866                    .and_then(|it| it.collect::<Result<_, DeserializationError>>())
867                    .map_err(deser_error_replace_rust_name::<Self>)
868            }
869            _ => unreachable!("Should be prevented by typecheck"),
870        }
871    }
872}
873
874impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata> for BTreeSet<T>
875where
876    T: DeserializeValue<'frame, 'metadata> + Ord,
877{
878    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
879        // It only makes sense for Set to deserialize to BTreeSet.
880        // Deserializing List straight to BTreeSet would be lossy.
881        match typ {
882            ColumnType::Collection {
883                frozen: false,
884                typ: CollectionType::Set(_),
885            } => ListlikeIterator::<'frame, 'metadata, T>::type_check(typ)
886                .map_err(typck_error_replace_rust_name::<Self>),
887            _ => Err(mk_typck_err::<Self>(
888                typ,
889                SetOrListTypeCheckErrorKind::NotSet,
890            )),
891        }
892    }
893
894    fn deserialize(
895        typ: &'metadata ColumnType<'metadata>,
896        v: Option<FrameSlice<'frame>>,
897    ) -> Result<Self, DeserializationError> {
898        ListlikeIterator::<'frame, 'metadata, T>::deserialize(typ, v)
899            .and_then(|it| it.collect::<Result<_, DeserializationError>>())
900            .map_err(deser_error_replace_rust_name::<Self>)
901    }
902}
903
904impl<'frame, 'metadata, T, S> DeserializeValue<'frame, 'metadata> for HashSet<T, S>
905where
906    T: DeserializeValue<'frame, 'metadata> + Eq + Hash,
907    S: BuildHasher + Default + 'frame,
908{
909    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
910        // It only makes sense for Set to deserialize to HashSet.
911        // Deserializing List straight to HashSet would be lossy.
912        match typ {
913            ColumnType::Collection {
914                frozen: false,
915                typ: CollectionType::Set(_),
916            } => ListlikeIterator::<'frame, 'metadata, T>::type_check(typ)
917                .map_err(typck_error_replace_rust_name::<Self>),
918            _ => Err(mk_typck_err::<Self>(
919                typ,
920                SetOrListTypeCheckErrorKind::NotSet,
921            )),
922        }
923    }
924
925    fn deserialize(
926        typ: &'metadata ColumnType<'metadata>,
927        v: Option<FrameSlice<'frame>>,
928    ) -> Result<Self, DeserializationError> {
929        ListlikeIterator::<'frame, 'metadata, T>::deserialize(typ, v)
930            .and_then(|it| it.collect::<Result<_, DeserializationError>>())
931            .map_err(deser_error_replace_rust_name::<Self>)
932    }
933}
934
935/// A deserialization iterator over a CQL vector.
936///
937/// Deserialization of a vector is done in two ways, depending on the element type:
938/// 1. If the element type is of a fixed-length, the iterator reads
939///    a fixed, known number of bytes for each element and deserializes
940///    according to the element type. The element count and element size
941///    are not encoded as the count is known from the vector type
942///    and the size is known from the element type.
943///
944/// 2. If the element type is of a variable-length, the iterator reads an vint
945///    (variable-length integer) for each element, which indicates the number of bytes
946///    to read for that element. Then, the iterator reads the specified number of bytes
947///    and deserializes according to the element type. This, however, is in contradiction
948///    with the CQL protocol, which specifies that the element count is encoded as a 4 byte int!
949///    Alas, Cassandra does not respect the protocol, so ScyllaDB and this driver have to follow.
950///
951/// It would be nice to have a rule to determine if the element type is fixed-length or not,
952/// however, we only have a heuristic. There are a few types that should, for all intents and purposes,
953/// be considered fixed-length, but are not, e.g TinyInt. See ColumnType::type_size() for the list.
954#[derive(Debug, Clone)]
955pub struct VectorIterator<'frame, 'metadata, T> {
956    collection_type: &'metadata ColumnType<'metadata>,
957    element_type: &'metadata ColumnType<'metadata>,
958    remaining: usize,
959    element_length: Option<usize>,
960    slice: FrameSlice<'frame>,
961    phantom_data: std::marker::PhantomData<T>,
962}
963
964impl<'frame, 'metadata, T> VectorIterator<'frame, 'metadata, T> {
965    fn new(
966        collection_type: &'metadata ColumnType<'metadata>,
967        element_type: &'metadata ColumnType<'metadata>,
968        count: usize,
969        element_length: Option<usize>,
970        slice: FrameSlice<'frame>,
971    ) -> Self {
972        Self {
973            collection_type,
974            element_type,
975            remaining: count,
976            element_length,
977            slice,
978            phantom_data: std::marker::PhantomData,
979        }
980    }
981}
982
983impl<'frame, 'metadata, T> DeserializeValue<'frame, 'metadata>
984    for VectorIterator<'frame, 'metadata, T>
985where
986    T: DeserializeValue<'frame, 'metadata>,
987{
988    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
989        match typ {
990            ColumnType::Vector { typ: t, .. } => {
991                <T as DeserializeValue<'frame, 'metadata>>::type_check(t).map_err(|err| {
992                    mk_typck_err::<Self>(typ, VectorTypeCheckErrorKind::ElementTypeCheckFailed(err))
993                })?;
994                Ok(())
995            }
996            _ => Err(mk_typck_err::<Self>(
997                typ,
998                VectorTypeCheckErrorKind::NotVector,
999            )),
1000        }
1001    }
1002
1003    fn deserialize(
1004        typ: &'metadata ColumnType<'metadata>,
1005        v: Option<FrameSlice<'frame>>,
1006    ) -> Result<Self, DeserializationError> {
1007        let (element_type, dimensions) = match typ {
1008            ColumnType::Vector {
1009                typ: element_type,
1010                dimensions,
1011            } => (element_type, dimensions),
1012            _ => {
1013                unreachable!("Typecheck should have prevented this scenario!")
1014            }
1015        };
1016
1017        let v = ensure_not_null_frame_slice::<Self>(typ, v)?;
1018
1019        Ok(Self::new(
1020            typ,
1021            element_type,
1022            *dimensions as usize,
1023            element_type.type_size(),
1024            v,
1025        ))
1026    }
1027}
1028
1029impl<'frame, 'metadata, T> VectorIterator<'frame, 'metadata, T>
1030where
1031    T: DeserializeValue<'frame, 'metadata>,
1032{
1033    fn next_constant_length_elem(
1034        &mut self,
1035        element_length: usize,
1036    ) -> Option<<Self as Iterator>::Item> {
1037        self.remaining = self.remaining.checked_sub(1)?;
1038        let raw = self.slice.read_n_bytes(element_length).map_err(|err| {
1039            mk_deser_err::<Self>(
1040                self.collection_type,
1041                BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
1042            )
1043        });
1044        Some(raw.and_then(|raw| {
1045            T::deserialize(self.element_type, raw).map_err(|err| {
1046                mk_deser_err::<Self>(
1047                    self.collection_type,
1048                    VectorDeserializationErrorKind::ElementDeserializationFailed(err),
1049                )
1050            })
1051        }))
1052    }
1053
1054    fn next_variable_length_elem(&mut self) -> Option<<Self as Iterator>::Item> {
1055        self.remaining = self.remaining.checked_sub(1)?;
1056        let size = types::unsigned_vint_decode(self.slice.as_slice_mut()).map_err(|err| {
1057            mk_deser_err::<Self>(
1058                self.collection_type,
1059                BuiltinDeserializationErrorKind::RawCqlBytesReadError(
1060                    LowLevelDeserializationError::IoError(Arc::new(err)),
1061                ),
1062            )
1063        });
1064        let raw = size
1065            .and_then(|size| {
1066                size.try_into().map_err(|_| {
1067                    mk_deser_err::<Self>(
1068                        self.collection_type,
1069                        BuiltinDeserializationErrorKind::ValueOverflow,
1070                    )
1071                })
1072            })
1073            .and_then(|size: usize| {
1074                self.slice.read_n_bytes(size).map_err(|err| {
1075                    mk_deser_err::<Self>(
1076                        self.collection_type,
1077                        BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
1078                    )
1079                })
1080            });
1081
1082        Some(raw.and_then(|raw| {
1083            T::deserialize(self.element_type, raw).map_err(|err| {
1084                mk_deser_err::<Self>(
1085                    self.element_type,
1086                    VectorDeserializationErrorKind::ElementDeserializationFailed(err),
1087                )
1088            })
1089        }))
1090    }
1091}
1092
1093impl<'frame, 'metadata, T> Iterator for VectorIterator<'frame, 'metadata, T>
1094where
1095    T: DeserializeValue<'frame, 'metadata>,
1096{
1097    type Item = Result<T, DeserializationError>;
1098
1099    fn next(&mut self) -> Option<Self::Item> {
1100        match self.element_length {
1101            Some(element_length) => self.next_constant_length_elem(element_length),
1102            None => self.next_variable_length_elem(),
1103        }
1104    }
1105
1106    #[inline]
1107    fn size_hint(&self) -> (usize, Option<usize>) {
1108        (self.remaining, Some(self.remaining))
1109    }
1110}
1111
1112/// An iterator over a CQL map.
1113#[derive(Debug, Clone)]
1114pub struct MapIterator<'frame, 'metadata, K, V> {
1115    coll_typ: &'metadata ColumnType<'metadata>,
1116    k_typ: &'metadata ColumnType<'metadata>,
1117    v_typ: &'metadata ColumnType<'metadata>,
1118    raw_iter: FixedLengthBytesSequenceIterator<'frame>,
1119    phantom_data_k: std::marker::PhantomData<K>,
1120    phantom_data_v: std::marker::PhantomData<V>,
1121}
1122
1123impl<'frame, 'metadata, K, V> MapIterator<'frame, 'metadata, K, V> {
1124    fn new(
1125        coll_typ: &'metadata ColumnType<'metadata>,
1126        k_typ: &'metadata ColumnType<'metadata>,
1127        v_typ: &'metadata ColumnType<'metadata>,
1128        count: usize,
1129        slice: FrameSlice<'frame>,
1130    ) -> Self {
1131        Self {
1132            coll_typ,
1133            k_typ,
1134            v_typ,
1135            raw_iter: FixedLengthBytesSequenceIterator::new(count, slice),
1136            phantom_data_k: std::marker::PhantomData,
1137            phantom_data_v: std::marker::PhantomData,
1138        }
1139    }
1140
1141    fn empty(
1142        coll_typ: &'metadata ColumnType<'metadata>,
1143        k_typ: &'metadata ColumnType<'metadata>,
1144        v_typ: &'metadata ColumnType<'metadata>,
1145    ) -> Self {
1146        Self {
1147            coll_typ,
1148            k_typ,
1149            v_typ,
1150            raw_iter: FixedLengthBytesSequenceIterator::empty(),
1151            phantom_data_k: std::marker::PhantomData,
1152            phantom_data_v: std::marker::PhantomData,
1153        }
1154    }
1155}
1156
1157impl<'frame, 'metadata, K, V> DeserializeValue<'frame, 'metadata>
1158    for MapIterator<'frame, 'metadata, K, V>
1159where
1160    K: DeserializeValue<'frame, 'metadata>,
1161    V: DeserializeValue<'frame, 'metadata>,
1162{
1163    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1164        match typ {
1165            ColumnType::Collection {
1166                frozen: false,
1167                typ: CollectionType::Map(k_t, v_t),
1168            } => {
1169                <K as DeserializeValue<'frame, 'metadata>>::type_check(k_t).map_err(|err| {
1170                    mk_typck_err::<Self>(typ, MapTypeCheckErrorKind::KeyTypeCheckFailed(err))
1171                })?;
1172                <V as DeserializeValue<'frame, 'metadata>>::type_check(v_t).map_err(|err| {
1173                    mk_typck_err::<Self>(typ, MapTypeCheckErrorKind::ValueTypeCheckFailed(err))
1174                })?;
1175                Ok(())
1176            }
1177            _ => Err(mk_typck_err::<Self>(typ, MapTypeCheckErrorKind::NotMap)),
1178        }
1179    }
1180
1181    fn deserialize(
1182        typ: &'metadata ColumnType<'metadata>,
1183        v: Option<FrameSlice<'frame>>,
1184    ) -> Result<Self, DeserializationError> {
1185        let (k_typ, v_typ) = match typ {
1186            ColumnType::Collection {
1187                frozen: false,
1188                typ: CollectionType::Map(k_t, v_t),
1189            } => (k_t, v_t),
1190            _ => {
1191                unreachable!("Typecheck should have prevented this scenario!")
1192            }
1193        };
1194
1195        let mut v = if let Some(v) = v {
1196            v
1197        } else {
1198            return Ok(Self::empty(typ, k_typ, v_typ));
1199        };
1200
1201        let count = types::read_int_length(v.as_slice_mut()).map_err(|err| {
1202            mk_deser_err::<Self>(
1203                typ,
1204                MapDeserializationErrorKind::LengthDeserializationFailed(
1205                    DeserializationError::new(err),
1206                ),
1207            )
1208        })?;
1209
1210        Ok(Self::new(typ, k_typ, v_typ, 2 * count, v))
1211    }
1212}
1213
1214impl<'frame, 'metadata, K, V> Iterator for MapIterator<'frame, 'metadata, K, V>
1215where
1216    K: DeserializeValue<'frame, 'metadata>,
1217    V: DeserializeValue<'frame, 'metadata>,
1218{
1219    type Item = Result<(K, V), DeserializationError>;
1220
1221    fn next(&mut self) -> Option<Self::Item> {
1222        let raw_k = match self.raw_iter.next() {
1223            Some(Ok(raw_k)) => raw_k,
1224            Some(Err(err)) => {
1225                return Some(Err(mk_deser_err::<Self>(
1226                    self.coll_typ,
1227                    BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
1228                )));
1229            }
1230            None => return None,
1231        };
1232        let raw_v = match self.raw_iter.next() {
1233            Some(Ok(raw_v)) => raw_v,
1234            Some(Err(err)) => {
1235                return Some(Err(mk_deser_err::<Self>(
1236                    self.coll_typ,
1237                    BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
1238                )));
1239            }
1240            None => return None,
1241        };
1242
1243        let do_next = || -> Result<(K, V), DeserializationError> {
1244            let k = K::deserialize(self.k_typ, raw_k).map_err(|err| {
1245                mk_deser_err::<Self>(
1246                    self.coll_typ,
1247                    MapDeserializationErrorKind::KeyDeserializationFailed(err),
1248                )
1249            })?;
1250            let v = V::deserialize(self.v_typ, raw_v).map_err(|err| {
1251                mk_deser_err::<Self>(
1252                    self.coll_typ,
1253                    MapDeserializationErrorKind::ValueDeserializationFailed(err),
1254                )
1255            })?;
1256            Ok((k, v))
1257        };
1258        Some(do_next())
1259    }
1260
1261    fn size_hint(&self) -> (usize, Option<usize>) {
1262        self.raw_iter.size_hint()
1263    }
1264}
1265
1266impl<'frame, 'metadata, K, V> DeserializeValue<'frame, 'metadata> for BTreeMap<K, V>
1267where
1268    K: DeserializeValue<'frame, 'metadata> + Ord,
1269    V: DeserializeValue<'frame, 'metadata>,
1270{
1271    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1272        MapIterator::<'frame, 'metadata, K, V>::type_check(typ)
1273            .map_err(typck_error_replace_rust_name::<Self>)
1274    }
1275
1276    fn deserialize(
1277        typ: &'metadata ColumnType<'metadata>,
1278        v: Option<FrameSlice<'frame>>,
1279    ) -> Result<Self, DeserializationError> {
1280        MapIterator::<'frame, 'metadata, K, V>::deserialize(typ, v)
1281            .and_then(|it| it.collect::<Result<_, DeserializationError>>())
1282            .map_err(deser_error_replace_rust_name::<Self>)
1283    }
1284}
1285
1286impl<'frame, 'metadata, K, V, S> DeserializeValue<'frame, 'metadata> for HashMap<K, V, S>
1287where
1288    K: DeserializeValue<'frame, 'metadata> + Eq + Hash,
1289    V: DeserializeValue<'frame, 'metadata>,
1290    S: BuildHasher + Default + 'frame,
1291{
1292    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1293        MapIterator::<'frame, 'metadata, K, V>::type_check(typ)
1294            .map_err(typck_error_replace_rust_name::<Self>)
1295    }
1296
1297    fn deserialize(
1298        typ: &'metadata ColumnType<'metadata>,
1299        v: Option<FrameSlice<'frame>>,
1300    ) -> Result<Self, DeserializationError> {
1301        MapIterator::<'frame, 'metadata, K, V>::deserialize(typ, v)
1302            .and_then(|it| it.collect::<Result<_, DeserializationError>>())
1303            .map_err(deser_error_replace_rust_name::<Self>)
1304    }
1305}
1306
1307// tuples
1308
1309// Implements tuple deserialization.
1310// The generated impl expects that the serialized data contains exactly the given amount of values.
1311macro_rules! impl_tuple {
1312    ($($Ti:ident),*; $($idx:literal),*; $($idf:ident),*) => {
1313        impl<'frame, 'metadata, $($Ti),*> DeserializeValue<'frame, 'metadata> for ($($Ti,)*)
1314        where
1315            $($Ti: DeserializeValue<'frame, 'metadata>),*
1316        {
1317            fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1318                const TUPLE_LEN: usize = (&[$($idx),*] as &[i32]).len();
1319                let [$($idf),*] = ensure_tuple_type::<($($Ti,)*), TUPLE_LEN>(typ)?;
1320                $(
1321                    <$Ti>::type_check($idf).map_err(|err| mk_typck_err::<Self>(
1322                        typ,
1323                        TupleTypeCheckErrorKind::FieldTypeCheckFailed {
1324                            position: $idx,
1325                            err,
1326                        }
1327                    ))?;
1328                )*
1329                Ok(())
1330            }
1331
1332            fn deserialize(typ: &'metadata ColumnType<'metadata>, v: Option<FrameSlice<'frame>>) -> Result<Self, DeserializationError> {
1333                const TUPLE_LEN: usize = (&[$($idx),*] as &[i32]).len();
1334                // Safety: we are allowed to assume that type_check() was already called.
1335                let [$($idf),*] = ensure_tuple_type::<($($Ti,)*), TUPLE_LEN>(typ)
1336                    .expect("Type check should have prevented this!");
1337
1338                // Ignore the warning for the zero-sized tuple
1339                #[allow(unused)]
1340                let mut v = ensure_not_null_frame_slice::<Self>(typ, v)?;
1341                let ret = (
1342                    $(
1343                        {
1344                            let cql_bytes = if v.is_empty() {
1345                                // Special case: if there are no bytes left to read, consider the tuple element as null.
1346                                // This is needed to handle tuples with less elements than expected
1347                                // (see https://github.com/scylladb/scylla-rust-driver/issues/1452 for context).
1348                                None
1349                            } else {
1350                                v.read_cql_bytes().map_err(|err| DeserializationError::new(err))?
1351                            };
1352
1353                            <$Ti>::deserialize($idf, cql_bytes)
1354                                .map_err(|err| mk_deser_err::<Self>(
1355                                    typ,
1356                                    TupleDeserializationErrorKind::FieldDeserializationFailed {
1357                                        position: $idx,
1358                                        err,
1359                                    }
1360                                )
1361                            )?
1362                        },
1363                    )*
1364                );
1365                Ok(ret)
1366            }
1367        }
1368    }
1369}
1370
1371// Implements tuple deserialization for all tuple sizes up to predefined size.
1372// Accepts 3 lists, (see usage below the definition):
1373// - type parameters for the consecutive fields,
1374// - indices of the consecutive fields,
1375// - consecutive names for variables corresponding to each field.
1376//
1377// The idea is to recursively build prefixes of those lists (starting with an empty prefix)
1378// and for each prefix, implement deserialization for generic tuple represented by it.
1379// The < > brackets aid syntactically to separate the prefixes (positioned inside them)
1380// from the remaining suffixes (positioned beyond them).
1381macro_rules! impl_tuple_multiple {
1382    // The entry point to the macro.
1383    // Begins with implementing deserialization for (), then proceeds to the main recursive call.
1384    ($($Ti:ident),*; $($idx:literal),*; $($idf:ident),*) => {
1385        impl_tuple!(;;);
1386        impl_tuple_multiple!(
1387            $($Ti),* ; < > ;
1388            $($idx),*; < > ;
1389            $($idf),*; < >
1390        );
1391    };
1392
1393    // The termination condition. No more fields given to extend the tuple with.
1394    (;< $($Ti:ident,)* >;;< $($idx:literal,)* >;;< $($idf:ident,)* >) => {};
1395
1396    // The recursion. Upon each call, a new field is appended to the tuple
1397    // and deserialization is implemented for it.
1398    (
1399        $T_head:ident $(,$T_suffix:ident)*; < $($T_prefix:ident,)* > ;
1400        $idx_head:literal $(,$idx_suffix:literal)*; < $($idx_prefix:literal,)* >;
1401        $idf_head:ident $(,$idf_suffix:ident)* ; <$($idf_prefix:ident,)*>
1402    ) => {
1403        impl_tuple!(
1404            $($T_prefix,)* $T_head;
1405            $($idx_prefix, )* $idx_head;
1406            $($idf_prefix, )* $idf_head
1407        );
1408        impl_tuple_multiple!(
1409            $($T_suffix),* ; < $($T_prefix,)* $T_head, > ;
1410            $($idx_suffix),*; < $($idx_prefix, )* $idx_head, > ;
1411            $($idf_suffix),*; < $($idf_prefix, )* $idf_head, >
1412        );
1413    }
1414}
1415
1416pub(super) use impl_tuple_multiple;
1417
1418// Implements tuple deserialization for all tuple sizes up to 16.
1419impl_tuple_multiple!(
1420    T0, T1, T2, T3, T4, T5, T6, T7, T8, T9, T10, T11, T12, T13, T14, T15;
1421    0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15;
1422    t0, t1, t2, t3, t4, t5, t6, t7, t8, t9, t10, t11, t12, t13, t14, t15
1423);
1424
1425// udts
1426
1427/// An iterator over fields of a User Defined Type.
1428///
1429/// # Note
1430///
1431/// A serialized UDT will generally have one value for each field, but it is
1432/// allowed to have fewer. This iterator differentiates null values
1433/// from non-existent values in the following way:
1434///
1435/// - `None` - missing from the serialized form
1436/// - `Some(None)` - present, but null
1437/// - `Some(Some(...))` - non-null, present value
1438#[derive(Debug, Clone)]
1439pub struct UdtIterator<'frame, 'metadata> {
1440    all_fields: &'metadata [(Cow<'metadata, str>, ColumnType<'metadata>)],
1441    type_name: &'metadata str,
1442    keyspace: &'metadata str,
1443    remaining_fields: &'metadata [(Cow<'metadata, str>, ColumnType<'metadata>)],
1444    raw_iter: BytesSequenceIterator<'frame>,
1445}
1446
1447impl<'frame, 'metadata> UdtIterator<'frame, 'metadata> {
1448    fn new(
1449        fields: &'metadata [(Cow<'metadata, str>, ColumnType<'metadata>)],
1450        type_name: &'metadata str,
1451        keyspace: &'metadata str,
1452        slice: FrameSlice<'frame>,
1453    ) -> Self {
1454        Self {
1455            all_fields: fields,
1456            remaining_fields: fields,
1457            type_name,
1458            keyspace,
1459            raw_iter: BytesSequenceIterator::new(slice),
1460        }
1461    }
1462
1463    /// Returns remaining (i.e., not yet deserialized) fields of the UDT.
1464    #[inline]
1465    pub fn fields(&self) -> &'metadata [(Cow<'metadata, str>, ColumnType<'metadata>)] {
1466        self.remaining_fields
1467    }
1468}
1469
1470impl<'frame, 'metadata> DeserializeValue<'frame, 'metadata> for UdtIterator<'frame, 'metadata> {
1471    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1472        match typ {
1473            ColumnType::UserDefinedType { .. } => Ok(()),
1474            _ => Err(mk_typck_err::<Self>(typ, UdtTypeCheckErrorKind::NotUdt)),
1475        }
1476    }
1477
1478    fn deserialize(
1479        typ: &'metadata ColumnType<'metadata>,
1480        v: Option<FrameSlice<'frame>>,
1481    ) -> Result<Self, DeserializationError> {
1482        let v = ensure_not_null_frame_slice::<Self>(typ, v)?;
1483        let (fields, type_name, keyspace) = match typ {
1484            ColumnType::UserDefinedType {
1485                definition: udt, ..
1486            } => (
1487                udt.field_types.as_ref(),
1488                udt.name.as_ref(),
1489                udt.keyspace.as_ref(),
1490            ),
1491            _ => {
1492                unreachable!("Typecheck should have prevented this scenario!")
1493            }
1494        };
1495        Ok(Self::new(fields, type_name, keyspace, v))
1496    }
1497}
1498
1499impl<'frame, 'metadata> Iterator for UdtIterator<'frame, 'metadata> {
1500    type Item = (
1501        &'metadata (Cow<'metadata, str>, ColumnType<'metadata>),
1502        Result<Option<Option<FrameSlice<'frame>>>, DeserializationError>,
1503    );
1504
1505    fn next(&mut self) -> Option<Self::Item> {
1506        // TODO: Should we fail when there are too many fields?
1507        let (head, fields) = self.remaining_fields.split_first()?;
1508        self.remaining_fields = fields;
1509        let raw_res = match self.raw_iter.next() {
1510            // The field is there and it was parsed correctly
1511            Some(Ok(raw)) => Ok(Some(raw)),
1512
1513            // There were some bytes but they didn't parse as correct field value
1514            Some(Err(err)) => Err(mk_deser_err::<Self>(
1515                &ColumnType::UserDefinedType {
1516                    frozen: false,
1517                    definition: Arc::new(UserDefinedType {
1518                        name: self.type_name.into(),
1519                        keyspace: self.keyspace.into(),
1520                        field_types: self.all_fields.to_owned(),
1521                    }),
1522                },
1523                BuiltinDeserializationErrorKind::RawCqlBytesReadError(err),
1524            )),
1525
1526            // The field is just missing from the serialized form
1527            None => Ok(None),
1528        };
1529        Some((head, raw_res))
1530    }
1531
1532    fn size_hint(&self) -> (usize, Option<usize>) {
1533        self.raw_iter.size_hint()
1534    }
1535}
1536
1537// Container implementations
1538
1539impl<'frame, 'metadata, T: DeserializeValue<'frame, 'metadata>> DeserializeValue<'frame, 'metadata>
1540    for Box<T>
1541{
1542    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1543        T::type_check(typ).map_err(typck_error_replace_rust_name::<Self>)
1544    }
1545
1546    fn deserialize(
1547        typ: &'metadata ColumnType<'metadata>,
1548        v: Option<FrameSlice<'frame>>,
1549    ) -> Result<Self, DeserializationError> {
1550        T::deserialize(typ, v)
1551            .map(Box::new)
1552            .map_err(deser_error_replace_rust_name::<Self>)
1553    }
1554}
1555
1556impl<'frame, 'metadata, T: DeserializeValue<'frame, 'metadata>> DeserializeValue<'frame, 'metadata>
1557    for Arc<T>
1558{
1559    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1560        T::type_check(typ).map_err(typck_error_replace_rust_name::<Self>)
1561    }
1562
1563    fn deserialize(
1564        typ: &'metadata ColumnType<'metadata>,
1565        v: Option<FrameSlice<'frame>>,
1566    ) -> Result<Self, DeserializationError> {
1567        T::deserialize(typ, v)
1568            .map(Arc::new)
1569            .map_err(deser_error_replace_rust_name::<Self>)
1570    }
1571}
1572
1573// Special cases for Box<str> and Arc<str>
1574// The generic implementations above don't work for str. This is because
1575// DeserializeValue is implemented for &str, but not for str. We can't change this:
1576// the type for DeserializeValue must be Sized because it is returned from deserialize method.
1577
1578impl<'frame, 'metadata> DeserializeValue<'frame, 'metadata> for Box<str> {
1579    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1580        <String as DeserializeValue>::type_check(typ).map_err(typck_error_replace_rust_name::<Self>)
1581    }
1582
1583    fn deserialize(
1584        typ: &'metadata ColumnType<'metadata>,
1585        v: Option<FrameSlice<'frame>>,
1586    ) -> Result<Self, DeserializationError> {
1587        String::deserialize(typ, v)
1588            .map(String::into_boxed_str)
1589            .map_err(deser_error_replace_rust_name::<Self>)
1590    }
1591}
1592
1593impl<'frame, 'metadata> DeserializeValue<'frame, 'metadata> for Arc<str> {
1594    fn type_check(typ: &ColumnType) -> Result<(), TypeCheckError> {
1595        <&str as DeserializeValue>::type_check(typ).map_err(typck_error_replace_rust_name::<Self>)
1596    }
1597
1598    fn deserialize(
1599        typ: &'metadata ColumnType<'metadata>,
1600        v: Option<FrameSlice<'frame>>,
1601    ) -> Result<Self, DeserializationError> {
1602        <&str as DeserializeValue>::deserialize(typ, v)
1603            .map(Into::<Arc<str>>::into)
1604            .map_err(deser_error_replace_rust_name::<Self>)
1605    }
1606}
1607
1608// Utilities
1609
1610fn ensure_not_null_frame_slice<'frame, T>(
1611    typ: &ColumnType,
1612    v: Option<FrameSlice<'frame>>,
1613) -> Result<FrameSlice<'frame>, DeserializationError> {
1614    v.ok_or_else(|| mk_deser_err::<T>(typ, BuiltinDeserializationErrorKind::ExpectedNonNull))
1615}
1616
1617fn ensure_not_null_slice<'frame, T>(
1618    typ: &ColumnType,
1619    v: Option<FrameSlice<'frame>>,
1620) -> Result<&'frame [u8], DeserializationError> {
1621    ensure_not_null_frame_slice::<T>(typ, v).map(|frame_slice| frame_slice.as_slice())
1622}
1623
1624fn ensure_not_null_owned<T>(
1625    typ: &ColumnType,
1626    v: Option<FrameSlice>,
1627) -> Result<Bytes, DeserializationError> {
1628    ensure_not_null_frame_slice::<T>(typ, v).map(|frame_slice| frame_slice.to_bytes())
1629}
1630
1631fn ensure_exact_length<'frame, T, const SIZE: usize>(
1632    typ: &ColumnType,
1633    v: &'frame [u8],
1634) -> Result<&'frame [u8; SIZE], DeserializationError> {
1635    v.try_into().map_err(|_| {
1636        mk_deser_err::<T>(
1637            typ,
1638            BuiltinDeserializationErrorKind::ByteLengthMismatch {
1639                expected: SIZE,
1640                got: v.len(),
1641            },
1642        )
1643    })
1644}
1645
1646fn ensure_tuple_type<'a, 'b, T, const SIZE: usize>(
1647    typ: &'b ColumnType<'a>,
1648) -> Result<&'b [ColumnType<'a>; SIZE], TypeCheckError> {
1649    if let ColumnType::Tuple(typs_v) = typ {
1650        typs_v.as_slice().try_into().map_err(|_| {
1651            BuiltinTypeCheckErrorKind::TupleError(TupleTypeCheckErrorKind::WrongElementCount {
1652                rust_type_el_count: SIZE,
1653                cql_type_el_count: typs_v.len(),
1654            })
1655        })
1656    } else {
1657        Err(BuiltinTypeCheckErrorKind::TupleError(
1658            TupleTypeCheckErrorKind::NotTuple,
1659        ))
1660    }
1661    .map_err(|kind| mk_typck_err::<T>(typ, kind))
1662}
1663
1664// Helper iterators
1665
1666/// Iterates over a sequence of `[bytes]` items from a frame subslice, expecting
1667/// a particular number of items.
1668///
1669/// The iterator does not consider it to be an error if there are some bytes
1670/// remaining in the slice after parsing requested amount of items.
1671#[derive(Clone, Copy, Debug)]
1672pub struct FixedLengthBytesSequenceIterator<'frame> {
1673    slice: FrameSlice<'frame>,
1674    remaining: usize,
1675}
1676
1677impl<'frame> FixedLengthBytesSequenceIterator<'frame> {
1678    fn new(count: usize, slice: FrameSlice<'frame>) -> Self {
1679        Self {
1680            slice,
1681            remaining: count,
1682        }
1683    }
1684
1685    fn empty() -> Self {
1686        Self {
1687            slice: FrameSlice::new_empty(),
1688            remaining: 0,
1689        }
1690    }
1691}
1692
1693impl<'frame> Iterator for FixedLengthBytesSequenceIterator<'frame> {
1694    type Item = Result<Option<FrameSlice<'frame>>, LowLevelDeserializationError>;
1695
1696    fn next(&mut self) -> Option<Self::Item> {
1697        self.remaining = self.remaining.checked_sub(1)?;
1698        Some(self.slice.read_cql_bytes())
1699    }
1700}
1701
1702/// Iterates over a sequence of `[bytes]` items from a frame subslice.
1703///
1704/// The `[bytes]` items are parsed until the end of subslice is reached.
1705#[derive(Clone, Copy, Debug)]
1706pub struct BytesSequenceIterator<'frame> {
1707    slice: FrameSlice<'frame>,
1708}
1709
1710impl<'frame> BytesSequenceIterator<'frame> {
1711    fn new(slice: FrameSlice<'frame>) -> Self {
1712        Self { slice }
1713    }
1714}
1715
1716impl<'frame> From<FrameSlice<'frame>> for BytesSequenceIterator<'frame> {
1717    #[inline]
1718    fn from(slice: FrameSlice<'frame>) -> Self {
1719        Self::new(slice)
1720    }
1721}
1722
1723impl<'frame> Iterator for BytesSequenceIterator<'frame> {
1724    type Item = Result<Option<FrameSlice<'frame>>, LowLevelDeserializationError>;
1725
1726    fn next(&mut self) -> Option<Self::Item> {
1727        if self.slice.as_slice().is_empty() {
1728            None
1729        } else {
1730            Some(self.slice.read_cql_bytes())
1731        }
1732    }
1733}
1734
1735// Error facilities
1736
1737/// Type checking of one of the built-in types failed.
1738#[derive(Debug, Error, Clone)]
1739#[error("Failed to type check Rust type {rust_name} against CQL type {cql_type:?}: {kind}")]
1740pub struct BuiltinTypeCheckError {
1741    /// Name of the Rust type being deserialized.
1742    pub rust_name: &'static str,
1743
1744    /// The CQL type that the Rust type was being deserialized from.
1745    pub cql_type: ColumnType<'static>,
1746
1747    /// Detailed information about the failure.
1748    pub kind: BuiltinTypeCheckErrorKind,
1749}
1750
1751// Not part of the public API; used in derive macros.
1752#[doc(hidden)]
1753pub fn mk_typck_err<T>(
1754    cql_type: &ColumnType,
1755    kind: impl Into<BuiltinTypeCheckErrorKind>,
1756) -> TypeCheckError {
1757    mk_typck_err_named(std::any::type_name::<T>(), cql_type, kind)
1758}
1759
1760fn mk_typck_err_named(
1761    name: &'static str,
1762    cql_type: &ColumnType,
1763    kind: impl Into<BuiltinTypeCheckErrorKind>,
1764) -> TypeCheckError {
1765    TypeCheckError::new(BuiltinTypeCheckError {
1766        rust_name: name,
1767        cql_type: cql_type.clone().into_owned(),
1768        kind: kind.into(),
1769    })
1770}
1771
1772macro_rules! exact_type_check {
1773    ($typ:ident, $($cql:tt),*) => {
1774        match $typ {
1775            $(ColumnType::Native(NativeType::$cql))|* => {},
1776            _ => return Err(mk_typck_err::<Self>(
1777                $typ,
1778                BuiltinTypeCheckErrorKind::MismatchedType {
1779                    expected: &[$(ColumnType::Native(NativeType::$cql)),*],
1780                }
1781            ))
1782        }
1783    };
1784}
1785use exact_type_check;
1786
1787/// Describes why type checking some of the built-in types failed.
1788#[derive(Debug, Clone)]
1789#[non_exhaustive]
1790pub enum BuiltinTypeCheckErrorKind {
1791    /// Expected one from a list of particular types.
1792    MismatchedType {
1793        /// The list of types that the Rust type can deserialize from.
1794        expected: &'static [ColumnType<'static>],
1795    },
1796
1797    /// A type check failure specific to a CQL set or list.
1798    SetOrListError(SetOrListTypeCheckErrorKind),
1799
1800    /// A type check failure specific to a CQL vector.
1801    VectorError(VectorTypeCheckErrorKind),
1802
1803    /// A type check failure specific to a CQL map.
1804    MapError(MapTypeCheckErrorKind),
1805
1806    /// A type check failure specific to a CQL tuple.
1807    TupleError(TupleTypeCheckErrorKind),
1808
1809    /// A type check failure specific to a CQL UDT.
1810    UdtError(UdtTypeCheckErrorKind),
1811
1812    /// A type check detected type not deserializable to a vector.
1813    NotDeserializableToVec,
1814}
1815
1816impl From<SetOrListTypeCheckErrorKind> for BuiltinTypeCheckErrorKind {
1817    #[inline]
1818    fn from(value: SetOrListTypeCheckErrorKind) -> Self {
1819        BuiltinTypeCheckErrorKind::SetOrListError(value)
1820    }
1821}
1822
1823impl From<VectorTypeCheckErrorKind> for BuiltinTypeCheckErrorKind {
1824    #[inline]
1825    fn from(value: VectorTypeCheckErrorKind) -> Self {
1826        BuiltinTypeCheckErrorKind::VectorError(value)
1827    }
1828}
1829
1830impl From<MapTypeCheckErrorKind> for BuiltinTypeCheckErrorKind {
1831    #[inline]
1832    fn from(value: MapTypeCheckErrorKind) -> Self {
1833        BuiltinTypeCheckErrorKind::MapError(value)
1834    }
1835}
1836
1837impl From<TupleTypeCheckErrorKind> for BuiltinTypeCheckErrorKind {
1838    #[inline]
1839    fn from(value: TupleTypeCheckErrorKind) -> Self {
1840        BuiltinTypeCheckErrorKind::TupleError(value)
1841    }
1842}
1843
1844impl From<UdtTypeCheckErrorKind> for BuiltinTypeCheckErrorKind {
1845    #[inline]
1846    fn from(value: UdtTypeCheckErrorKind) -> Self {
1847        BuiltinTypeCheckErrorKind::UdtError(value)
1848    }
1849}
1850
1851impl Display for BuiltinTypeCheckErrorKind {
1852    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1853        match self {
1854            BuiltinTypeCheckErrorKind::MismatchedType { expected } => {
1855                write!(f, "expected one of the CQL types: {expected:?}")
1856            }
1857            BuiltinTypeCheckErrorKind::SetOrListError(err) => err.fmt(f),
1858            BuiltinTypeCheckErrorKind::VectorError(err) => err.fmt(f),
1859            BuiltinTypeCheckErrorKind::MapError(err) => err.fmt(f),
1860            BuiltinTypeCheckErrorKind::TupleError(err) => err.fmt(f),
1861            BuiltinTypeCheckErrorKind::UdtError(err) => err.fmt(f),
1862            BuiltinTypeCheckErrorKind::NotDeserializableToVec => {
1863                f.write_str("the CQL type is not deserializable to a vector")
1864            }
1865        }
1866    }
1867}
1868
1869/// Describes why type checking of a set or list type failed.
1870#[derive(Debug, Clone)]
1871#[non_exhaustive]
1872pub enum SetOrListTypeCheckErrorKind {
1873    /// The CQL type is neither a set not a list.
1874    NotSetOrList,
1875    /// The CQL type is not a set.
1876    NotSet,
1877    /// Incompatible element types.
1878    ElementTypeCheckFailed(TypeCheckError),
1879}
1880
1881impl Display for SetOrListTypeCheckErrorKind {
1882    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1883        match self {
1884            SetOrListTypeCheckErrorKind::NotSetOrList => {
1885                f.write_str("the CQL type the Rust type was attempted to be type checked against was neither a set nor a list")
1886            }
1887            SetOrListTypeCheckErrorKind::NotSet => {
1888                f.write_str("the CQL type the Rust type was attempted to be type checked against was not a set")
1889            }
1890            SetOrListTypeCheckErrorKind::ElementTypeCheckFailed(err) => {
1891                write!(f, "the set or list element types between the CQL type and the Rust type failed to type check against each other: {err}")
1892            }
1893        }
1894    }
1895}
1896
1897/// Describes why type checking a vector type failed.
1898#[derive(Error, Debug, Clone)]
1899#[non_exhaustive]
1900pub enum VectorTypeCheckErrorKind {
1901    /// The CQL type is not a vector.
1902    #[error("the CQL type the Rust type was attempted to be type checked against was not a vector")]
1903    NotVector,
1904    /// Incompatible element types.
1905    #[error(
1906        "the vector element types between the CQL type and the Rust type failed to type check against each other: {0}"
1907    )]
1908    ElementTypeCheckFailed(TypeCheckError),
1909}
1910
1911/// Describes why type checking of a map type failed.
1912#[derive(Debug, Clone)]
1913#[non_exhaustive]
1914pub enum MapTypeCheckErrorKind {
1915    /// The CQL type is not a map.
1916    NotMap,
1917    /// Incompatible key types.
1918    KeyTypeCheckFailed(TypeCheckError),
1919    /// Incompatible value types.
1920    ValueTypeCheckFailed(TypeCheckError),
1921}
1922
1923impl Display for MapTypeCheckErrorKind {
1924    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1925        match self {
1926            MapTypeCheckErrorKind::NotMap => {
1927                f.write_str("the CQL type the Rust type was attempted to be type checked against was neither a map")
1928            }
1929            MapTypeCheckErrorKind::KeyTypeCheckFailed(err) => {
1930                write!(f, "the map key types between the CQL type and the Rust type failed to type check against each other: {err}")
1931            },
1932            MapTypeCheckErrorKind::ValueTypeCheckFailed(err) => {
1933                write!(f, "the map value types between the CQL type and the Rust type failed to type check against each other: {err}")
1934            },
1935        }
1936    }
1937}
1938
1939/// Describes why type checking of a tuple failed.
1940#[derive(Debug, Clone)]
1941#[non_exhaustive]
1942pub enum TupleTypeCheckErrorKind {
1943    /// The CQL type is not a tuple.
1944    NotTuple,
1945
1946    /// The tuple has the wrong element count.
1947    WrongElementCount {
1948        /// The number of elements that the Rust tuple has.
1949        rust_type_el_count: usize,
1950
1951        /// The number of elements that the CQL tuple type has.
1952        cql_type_el_count: usize,
1953    },
1954
1955    /// The CQL type and the Rust type of a tuple field failed to type check against each other.
1956    FieldTypeCheckFailed {
1957        /// The index of the field whose type check failed.
1958        position: usize,
1959
1960        /// The type check error that occurred.
1961        err: TypeCheckError,
1962    },
1963}
1964
1965impl Display for TupleTypeCheckErrorKind {
1966    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1967        match self {
1968            TupleTypeCheckErrorKind::NotTuple => write!(
1969                f,
1970                "the CQL type the tuple was attempted to be serialized to is not a tuple"
1971            ),
1972            TupleTypeCheckErrorKind::WrongElementCount {
1973                rust_type_el_count,
1974                cql_type_el_count,
1975            } => write!(
1976                f,
1977                "wrong tuple element count: CQL type has {cql_type_el_count}, the Rust tuple has {rust_type_el_count}"
1978            ),
1979
1980            TupleTypeCheckErrorKind::FieldTypeCheckFailed { position, err } => write!(
1981                f,
1982                "the CQL type and the Rust type of the tuple field {position} failed to type check against each other: {err}"
1983            ),
1984        }
1985    }
1986}
1987
1988/// Describes why type checking of a user defined type failed.
1989#[derive(Debug, Clone)]
1990#[non_exhaustive]
1991pub enum UdtTypeCheckErrorKind {
1992    /// The CQL type is not a user defined type.
1993    NotUdt,
1994
1995    /// The CQL UDT type does not have some fields that is required in the Rust struct.
1996    ValuesMissingForUdtFields {
1997        /// Names of fields that the Rust struct requires but are missing in the CQL UDT.
1998        field_names: Vec<&'static str>,
1999    },
2000
2001    /// A different field name was expected at given position.
2002    FieldNameMismatch {
2003        /// Index of the field in the Rust struct.
2004        position: usize,
2005
2006        /// The name of the Rust field.
2007        rust_field_name: String,
2008
2009        /// The name of the CQL UDT field.
2010        db_field_name: String,
2011    },
2012
2013    /// UDT contains an excess field, which does not correspond to any Rust struct's field.
2014    ExcessFieldInUdt {
2015        /// The name of the CQL UDT field.
2016        db_field_name: String,
2017    },
2018
2019    /// Duplicated field in serialized data.
2020    DuplicatedField {
2021        /// The name of the duplicated field.
2022        field_name: String,
2023    },
2024
2025    /// Fewer fields present in the UDT than required by the Rust type.
2026    TooFewFields {
2027        // TODO: decide whether we are OK with restricting to `&'static str` here.
2028        required_fields: Vec<&'static str>,
2029        present_fields: Vec<String>,
2030    },
2031
2032    /// Type check failed between UDT and Rust type field.
2033    FieldTypeCheckFailed {
2034        /// The name of the field whose type check failed.
2035        field_name: String,
2036
2037        /// Inner type check error that occurred.
2038        err: TypeCheckError,
2039    },
2040}
2041
2042impl Display for UdtTypeCheckErrorKind {
2043    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2044        match self {
2045            UdtTypeCheckErrorKind::NotUdt => write!(
2046                f,
2047                "the CQL type the Rust type was attempted to be type checked against is not a UDT"
2048            ),
2049            UdtTypeCheckErrorKind::ValuesMissingForUdtFields { field_names } => {
2050                write!(
2051                    f,
2052                    "the fields {field_names:?} are missing from the DB data but are required by the Rust type"
2053                )
2054            }
2055            UdtTypeCheckErrorKind::FieldNameMismatch {
2056                rust_field_name,
2057                db_field_name,
2058                position,
2059            } => write!(
2060                f,
2061                "expected field with name {db_field_name} at position {position}, but the Rust field name is {rust_field_name}"
2062            ),
2063            UdtTypeCheckErrorKind::ExcessFieldInUdt { db_field_name } => write!(
2064                f,
2065                "UDT contains an excess field {db_field_name}, which does not correspond to any Rust struct's field."
2066            ),
2067            UdtTypeCheckErrorKind::DuplicatedField { field_name } => write!(
2068                f,
2069                "field {field_name} occurs more than once in CQL UDT type"
2070            ),
2071            UdtTypeCheckErrorKind::TooFewFields {
2072                required_fields,
2073                present_fields,
2074            } => write!(
2075                f,
2076                "fewer fields present in the UDT than required by the Rust type: UDT has {present_fields:?}, Rust type requires {required_fields:?}",
2077            ),
2078            UdtTypeCheckErrorKind::FieldTypeCheckFailed { field_name, err } => write!(
2079                f,
2080                "the UDT field {field_name} types between the CQL type and the Rust type failed to type check against each other: {err}"
2081            ),
2082        }
2083    }
2084}
2085
2086/// Deserialization of one of the built-in types failed.
2087#[derive(Debug, Error, Clone)]
2088#[error("Failed to deserialize Rust type {rust_name} from CQL type {cql_type:?}: {kind}")]
2089pub struct BuiltinDeserializationError {
2090    /// Name of the Rust type being deserialized.
2091    pub rust_name: &'static str,
2092
2093    /// The CQL type that the Rust type was being deserialized from.
2094    pub cql_type: ColumnType<'static>,
2095
2096    /// Detailed information about the failure.
2097    pub kind: BuiltinDeserializationErrorKind,
2098}
2099
2100// Not part of the public API; used in derive macros.
2101#[doc(hidden)]
2102pub fn mk_deser_err<T>(
2103    cql_type: &ColumnType,
2104    kind: impl Into<BuiltinDeserializationErrorKind>,
2105) -> DeserializationError {
2106    mk_deser_err_named(std::any::type_name::<T>(), cql_type, kind)
2107}
2108
2109fn mk_deser_err_named(
2110    name: &'static str,
2111    cql_type: &ColumnType,
2112    kind: impl Into<BuiltinDeserializationErrorKind>,
2113) -> DeserializationError {
2114    DeserializationError::new(BuiltinDeserializationError {
2115        rust_name: name,
2116        cql_type: cql_type.clone().into_owned(),
2117        kind: kind.into(),
2118    })
2119}
2120
2121/// Describes why deserialization of some of the built-in types failed.
2122#[derive(Debug, Clone)]
2123#[non_exhaustive]
2124pub enum BuiltinDeserializationErrorKind {
2125    /// Failed to deserialize one of date's fields.
2126    BadDate {
2127        date_field: &'static str,
2128        err: LowLevelDeserializationError,
2129    },
2130
2131    /// Failed to deserialize decimal's scale.
2132    BadDecimalScale(LowLevelDeserializationError),
2133
2134    /// Failed to deserialize raw bytes of cql value.
2135    RawCqlBytesReadError(LowLevelDeserializationError),
2136
2137    /// Expected non-null value, got null.
2138    ExpectedNonNull,
2139
2140    /// The length of read value in bytes is different than expected for the Rust type.
2141    ByteLengthMismatch { expected: usize, got: usize },
2142
2143    /// Expected valid ASCII string.
2144    ExpectedAscii,
2145
2146    /// Invalid UTF-8 string.
2147    InvalidUtf8(std::str::Utf8Error),
2148
2149    /// The read value is out of range supported by the Rust type.
2150    // TODO: consider storing additional info here (what exactly did not fit and why)
2151    ValueOverflow,
2152
2153    /// The length of read value in bytes is not suitable for IP address.
2154    BadInetLength { got: usize },
2155
2156    /// A deserialization failure specific to a CQL set or list.
2157    SetOrListError(SetOrListDeserializationErrorKind),
2158
2159    /// A deserialization failure specific to a CQL vector.
2160    VectorError(VectorDeserializationErrorKind),
2161
2162    /// A deserialization failure specific to a CQL map.
2163    MapError(MapDeserializationErrorKind),
2164
2165    /// A deserialization failure specific to a CQL tuple.
2166    TupleError(TupleDeserializationErrorKind),
2167
2168    /// A deserialization failure specific to a CQL UDT.
2169    UdtError(UdtDeserializationErrorKind),
2170
2171    /// Deserialization of this CQL type is not supported by the driver.
2172    Unsupported,
2173}
2174
2175impl Display for BuiltinDeserializationErrorKind {
2176    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2177        match self {
2178            BuiltinDeserializationErrorKind::BadDate { date_field, err } => write!(
2179                f,
2180                "malformed {date_field} during 'date' deserialization: {err}"
2181            ),
2182            BuiltinDeserializationErrorKind::BadDecimalScale(err) => {
2183                write!(f, "malformed decimal's scale: {err}")
2184            }
2185            BuiltinDeserializationErrorKind::RawCqlBytesReadError(err) => {
2186                write!(f, "failed to read raw cql value bytes: {err}")
2187            }
2188            BuiltinDeserializationErrorKind::ExpectedNonNull => {
2189                f.write_str("expected a non-null value, got null")
2190            }
2191            BuiltinDeserializationErrorKind::ByteLengthMismatch { expected, got } => {
2192                write!(f, "the CQL type requires {expected} bytes, but got {got}",)
2193            }
2194            BuiltinDeserializationErrorKind::ExpectedAscii => {
2195                f.write_str("expected a valid ASCII string")
2196            }
2197            BuiltinDeserializationErrorKind::InvalidUtf8(err) => err.fmt(f),
2198            BuiltinDeserializationErrorKind::ValueOverflow => {
2199                // TODO: consider storing Arc<dyn Display/Debug> of the offending value
2200                // inside this variant for debug purposes.
2201                f.write_str("read value is out of representable range")
2202            }
2203            BuiltinDeserializationErrorKind::BadInetLength { got } => write!(
2204                f,
2205                "the length of read value in bytes ({got}) is not suitable for IP address; expected 4 or 16"
2206            ),
2207            BuiltinDeserializationErrorKind::SetOrListError(err) => err.fmt(f),
2208            BuiltinDeserializationErrorKind::VectorError(err) => err.fmt(f),
2209            BuiltinDeserializationErrorKind::MapError(err) => err.fmt(f),
2210            BuiltinDeserializationErrorKind::TupleError(err) => err.fmt(f),
2211            BuiltinDeserializationErrorKind::UdtError(err) => err.fmt(f),
2212            BuiltinDeserializationErrorKind::Unsupported => {
2213                f.write_str("deserialization of this CQL type is not supported by the driver")
2214            }
2215        }
2216    }
2217}
2218
2219/// Describes why deserialization of a set or list type failed.
2220#[derive(Debug, Clone)]
2221#[non_exhaustive]
2222pub enum SetOrListDeserializationErrorKind {
2223    /// Failed to deserialize set or list's length.
2224    LengthDeserializationFailed(DeserializationError),
2225
2226    /// One of the elements of the set/list failed to deserialize.
2227    ElementDeserializationFailed(DeserializationError),
2228}
2229
2230impl Display for SetOrListDeserializationErrorKind {
2231    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2232        match self {
2233            SetOrListDeserializationErrorKind::LengthDeserializationFailed(err) => {
2234                write!(f, "failed to deserialize set or list's length: {err}")
2235            }
2236            SetOrListDeserializationErrorKind::ElementDeserializationFailed(err) => {
2237                write!(f, "failed to deserialize one of the elements: {err}")
2238            }
2239        }
2240    }
2241}
2242
2243impl From<SetOrListDeserializationErrorKind> for BuiltinDeserializationErrorKind {
2244    #[inline]
2245    fn from(err: SetOrListDeserializationErrorKind) -> Self {
2246        Self::SetOrListError(err)
2247    }
2248}
2249
2250/// Describes why deserialization of a vector type failed.
2251#[derive(Error, Debug, Clone)]
2252#[non_exhaustive]
2253pub enum VectorDeserializationErrorKind {
2254    /// One of the elements of the vector failed to deserialize.
2255    #[error("failed to deserialize one of the elements: {0}")]
2256    ElementDeserializationFailed(DeserializationError),
2257}
2258
2259impl From<VectorDeserializationErrorKind> for BuiltinDeserializationErrorKind {
2260    #[inline]
2261    fn from(err: VectorDeserializationErrorKind) -> Self {
2262        Self::VectorError(err)
2263    }
2264}
2265
2266/// Describes why deserialization of a map type failed.
2267#[derive(Debug, Clone)]
2268#[non_exhaustive]
2269// Check triggers because all variants end with "DeserializationFailed".
2270// TODO(2.0): Remove the "DeserializationFailed" postfix from variants.
2271#[expect(clippy::enum_variant_names)]
2272pub enum MapDeserializationErrorKind {
2273    /// Failed to deserialize map's length.
2274    LengthDeserializationFailed(DeserializationError),
2275
2276    /// One of the keys in the map failed to deserialize.
2277    KeyDeserializationFailed(DeserializationError),
2278
2279    /// One of the values in the map failed to deserialize.
2280    ValueDeserializationFailed(DeserializationError),
2281}
2282
2283impl Display for MapDeserializationErrorKind {
2284    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2285        match self {
2286            MapDeserializationErrorKind::LengthDeserializationFailed(err) => {
2287                write!(f, "failed to deserialize map's length: {err}")
2288            }
2289            MapDeserializationErrorKind::KeyDeserializationFailed(err) => {
2290                write!(f, "failed to deserialize one of the keys: {err}")
2291            }
2292            MapDeserializationErrorKind::ValueDeserializationFailed(err) => {
2293                write!(f, "failed to deserialize one of the values: {err}")
2294            }
2295        }
2296    }
2297}
2298
2299impl From<MapDeserializationErrorKind> for BuiltinDeserializationErrorKind {
2300    fn from(err: MapDeserializationErrorKind) -> Self {
2301        Self::MapError(err)
2302    }
2303}
2304
2305/// Describes why deserialization of a tuple failed.
2306#[derive(Debug, Clone)]
2307#[non_exhaustive]
2308pub enum TupleDeserializationErrorKind {
2309    /// One of the tuple fields failed to deserialize.
2310    FieldDeserializationFailed {
2311        /// Index of the tuple field that failed to deserialize.
2312        position: usize,
2313
2314        /// The error that caused the tuple field deserialization to fail.
2315        err: DeserializationError,
2316    },
2317}
2318
2319impl Display for TupleDeserializationErrorKind {
2320    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2321        match self {
2322            TupleDeserializationErrorKind::FieldDeserializationFailed {
2323                position: index,
2324                err,
2325            } => {
2326                write!(f, "field no. {index} failed to deserialize: {err}")
2327            }
2328        }
2329    }
2330}
2331
2332impl From<TupleDeserializationErrorKind> for BuiltinDeserializationErrorKind {
2333    fn from(err: TupleDeserializationErrorKind) -> Self {
2334        Self::TupleError(err)
2335    }
2336}
2337
2338/// Describes why deserialization of a user defined type failed.
2339#[derive(Debug, Clone)]
2340#[non_exhaustive]
2341pub enum UdtDeserializationErrorKind {
2342    /// One of the fields failed to deserialize.
2343    FieldDeserializationFailed {
2344        /// Name of the field which failed to deserialize.
2345        field_name: String,
2346
2347        /// The error that caused the UDT field deserialization to fail.
2348        err: DeserializationError,
2349    },
2350}
2351
2352impl Display for UdtDeserializationErrorKind {
2353    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
2354        match self {
2355            UdtDeserializationErrorKind::FieldDeserializationFailed { field_name, err } => {
2356                write!(f, "field {field_name} failed to deserialize: {err}")
2357            }
2358        }
2359    }
2360}
2361
2362impl From<UdtDeserializationErrorKind> for BuiltinDeserializationErrorKind {
2363    fn from(err: UdtDeserializationErrorKind) -> Self {
2364        Self::UdtError(err)
2365    }
2366}
2367
2368#[cfg(test)]
2369#[path = "value_tests.rs"]
2370pub(crate) mod tests;
2371
2372/// ```compile_fail
2373///
2374/// #[derive(scylla_macros::DeserializeValue)]
2375/// #[scylla(crate = scylla_cql, skip_name_checks)]
2376/// struct TestUdt {}
2377/// ```
2378fn _test_udt_bad_attributes_skip_name_check_requires_enforce_order() {}
2379
2380/// ```compile_fail
2381///
2382/// #[derive(scylla_macros::DeserializeValue)]
2383/// #[scylla(crate = scylla_cql, flavor = "enforce_order", skip_name_checks)]
2384/// struct TestUdt {
2385///     #[scylla(rename = "b")]
2386///     a: i32,
2387/// }
2388/// ```
2389fn _test_udt_bad_attributes_skip_name_check_conflicts_with_rename() {}
2390
2391/// ```compile_fail
2392///
2393/// #[derive(scylla_macros::DeserializeValue)]
2394/// #[scylla(crate = scylla_cql)]
2395/// struct TestUdt {
2396///     #[scylla(rename = "b")]
2397///     a: i32,
2398///     b: String,
2399/// }
2400/// ```
2401fn _test_udt_bad_attributes_rename_collision_with_field() {}
2402
2403/// ```compile_fail
2404///
2405/// #[derive(scylla_macros::DeserializeValue)]
2406/// #[scylla(crate = scylla_cql)]
2407/// struct TestUdt {
2408///     #[scylla(rename = "c")]
2409///     a: i32,
2410///     #[scylla(rename = "c")]
2411///     b: String,
2412/// }
2413/// ```
2414fn _test_udt_bad_attributes_rename_collision_with_another_rename() {}
2415
2416/// ```compile_fail
2417///
2418/// #[derive(scylla_macros::DeserializeValue)]
2419/// #[scylla(crate = scylla_cql, flavor = "enforce_order", skip_name_checks)]
2420/// struct TestUdt {
2421///     a: i32,
2422///     #[scylla(allow_missing)]
2423///     b: bool,
2424///     c: String,
2425/// }
2426/// ```
2427fn _test_udt_bad_attributes_name_skip_name_checks_limitations_on_allow_missing() {}
2428
2429/// ```
2430/// #[derive(scylla_macros::DeserializeValue)]
2431/// #[scylla(crate = scylla_cql)]
2432/// struct TestUdt {
2433///     a: i32,
2434///     #[scylla(allow_missing)]
2435///     b: bool,
2436///     c: String,
2437/// }
2438/// ```
2439fn _test_udt_unordered_flavour_no_limitations_on_allow_missing() {}