[go: up one dir, main page]

bson/ser/
serde.rs

1use serde::ser::{
2    self,
3    Error as SerdeError,
4    Serialize,
5    SerializeMap,
6    SerializeSeq,
7    SerializeStruct,
8    SerializeStructVariant,
9    SerializeTuple,
10    SerializeTupleStruct,
11    SerializeTupleVariant,
12};
13
14use crate::{
15    base64,
16    bson::{Array, Bson, DbPointer, Document, JavaScriptCodeWithScope, Regex, Timestamp},
17    datetime::DateTime,
18    extjson,
19    oid::ObjectId,
20    raw::{RawDbPointerRef, RawRegexRef, RAW_ARRAY_NEWTYPE, RAW_DOCUMENT_NEWTYPE},
21    serde_helpers::HUMAN_READABLE_NEWTYPE,
22    spec::BinarySubtype,
23    uuid::UUID_NEWTYPE_NAME,
24    Binary,
25    Decimal128,
26};
27
28use super::{to_bson_with_options, Error};
29
30impl Serialize for ObjectId {
31    #[inline]
32    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
33    where
34        S: serde::ser::Serializer,
35    {
36        let mut ser = serializer.serialize_struct("$oid", 1)?;
37        ser.serialize_field("$oid", &self.to_string())?;
38        ser.end()
39    }
40}
41
42impl Serialize for Document {
43    #[inline]
44    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
45    where
46        S: ser::Serializer,
47    {
48        let mut state = serializer.serialize_map(Some(self.len()))?;
49        for (k, v) in self {
50            state.serialize_entry(k, v)?;
51        }
52        state.end()
53    }
54}
55
56impl Serialize for Bson {
57    #[inline]
58    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
59    where
60        S: ser::Serializer,
61    {
62        match self {
63            Bson::Double(v) => serializer.serialize_f64(*v),
64            Bson::String(v) => serializer.serialize_str(v),
65            Bson::Array(v) => v.serialize(serializer),
66            Bson::Document(v) => v.serialize(serializer),
67            Bson::Boolean(v) => serializer.serialize_bool(*v),
68            Bson::Null => serializer.serialize_unit(),
69            Bson::Int32(v) => serializer.serialize_i32(*v),
70            Bson::Int64(v) => serializer.serialize_i64(*v),
71            Bson::ObjectId(oid) => oid.serialize(serializer),
72            Bson::DateTime(dt) => dt.serialize(serializer),
73            Bson::Binary(b) => b.serialize(serializer),
74            Bson::JavaScriptCode(c) => {
75                let mut state = serializer.serialize_struct("$code", 1)?;
76                state.serialize_field("$code", c)?;
77                state.end()
78            }
79            Bson::JavaScriptCodeWithScope(code_w_scope) => code_w_scope.serialize(serializer),
80            Bson::DbPointer(dbp) => dbp.serialize(serializer),
81            Bson::Symbol(s) => {
82                let mut state = serializer.serialize_struct("$symbol", 1)?;
83                state.serialize_field("$symbol", s)?;
84                state.end()
85            }
86            Bson::RegularExpression(re) => re.serialize(serializer),
87            Bson::Timestamp(t) => t.serialize(serializer),
88            Bson::Decimal128(d) => d.serialize(serializer),
89            Bson::Undefined => {
90                let mut state = serializer.serialize_struct("$undefined", 1)?;
91                state.serialize_field("$undefined", &true)?;
92                state.end()
93            }
94            Bson::MaxKey => {
95                let mut state = serializer.serialize_struct("$maxKey", 1)?;
96                state.serialize_field("$maxKey", &1)?;
97                state.end()
98            }
99            Bson::MinKey => {
100                let mut state = serializer.serialize_struct("$minKey", 1)?;
101                state.serialize_field("$minKey", &1)?;
102                state.end()
103            }
104        }
105    }
106}
107
108/// Serde Serializer
109#[non_exhaustive]
110pub struct Serializer {
111    options: SerializerOptions,
112}
113
114/// Options used to configure a [`Serializer`].
115#[derive(Debug, Clone, Default)]
116#[non_exhaustive]
117pub struct SerializerOptions {
118    /// Whether the [`Serializer`] should present itself as human readable or not.
119    /// The default value is true.
120    #[deprecated = "use bson::serde_helpers::HumanReadable"]
121    pub human_readable: Option<bool>,
122}
123
124impl SerializerOptions {
125    /// Create a builder used to construct a new [`SerializerOptions`].
126    pub fn builder() -> SerializerOptionsBuilder {
127        SerializerOptionsBuilder {
128            options: Default::default(),
129        }
130    }
131}
132
133/// A builder used to construct new [`SerializerOptions`] structs.
134pub struct SerializerOptionsBuilder {
135    options: SerializerOptions,
136}
137
138impl SerializerOptionsBuilder {
139    /// Set the value for [`SerializerOptions::is_human_readable`].
140    #[deprecated = "use bson::serde_helpers::HumanReadable"]
141    #[allow(deprecated)]
142    pub fn human_readable(mut self, value: impl Into<Option<bool>>) -> Self {
143        self.options.human_readable = value.into();
144        self
145    }
146
147    /// Consume this builder and produce a [`SerializerOptions`].
148    pub fn build(self) -> SerializerOptions {
149        self.options
150    }
151}
152
153impl Serializer {
154    /// Construct a new [`Serializer`].
155    #[allow(clippy::new_without_default)]
156    pub fn new() -> Serializer {
157        Serializer {
158            options: Default::default(),
159        }
160    }
161
162    /// Construct a new [`Serializer`] configured with the provided [`SerializerOptions`].
163    pub fn new_with_options(options: SerializerOptions) -> Self {
164        Serializer { options }
165    }
166}
167
168impl ser::Serializer for Serializer {
169    type Ok = Bson;
170    type Error = Error;
171
172    type SerializeSeq = ArraySerializer;
173    type SerializeTuple = TupleSerializer;
174    type SerializeTupleStruct = TupleStructSerializer;
175    type SerializeTupleVariant = TupleVariantSerializer;
176    type SerializeMap = MapSerializer;
177    type SerializeStruct = StructSerializer;
178    type SerializeStructVariant = StructVariantSerializer;
179
180    #[inline]
181    fn serialize_bool(self, value: bool) -> crate::ser::Result<Bson> {
182        Ok(Bson::Boolean(value))
183    }
184
185    #[inline]
186    fn serialize_i8(self, value: i8) -> crate::ser::Result<Bson> {
187        self.serialize_i32(value as i32)
188    }
189
190    #[inline]
191    fn serialize_u8(self, value: u8) -> crate::ser::Result<Bson> {
192        Ok(Bson::Int32(value as i32))
193    }
194
195    #[inline]
196    fn serialize_i16(self, value: i16) -> crate::ser::Result<Bson> {
197        self.serialize_i32(value as i32)
198    }
199
200    #[inline]
201    fn serialize_u16(self, value: u16) -> crate::ser::Result<Bson> {
202        Ok(Bson::Int32(value as i32))
203    }
204
205    #[inline]
206    fn serialize_i32(self, value: i32) -> crate::ser::Result<Bson> {
207        Ok(Bson::Int32(value))
208    }
209
210    #[inline]
211    fn serialize_u32(self, value: u32) -> crate::ser::Result<Bson> {
212        Ok(Bson::Int64(value as i64))
213    }
214
215    #[inline]
216    fn serialize_i64(self, value: i64) -> crate::ser::Result<Bson> {
217        Ok(Bson::Int64(value))
218    }
219
220    #[inline]
221    fn serialize_u64(self, value: u64) -> crate::ser::Result<Bson> {
222        use std::convert::TryFrom;
223
224        match i64::try_from(value) {
225            Ok(ivalue) => Ok(Bson::Int64(ivalue)),
226            Err(_) => Err(Error::UnsignedIntegerExceededRange(value)),
227        }
228    }
229
230    #[inline]
231    fn serialize_f32(self, value: f32) -> crate::ser::Result<Bson> {
232        self.serialize_f64(value as f64)
233    }
234
235    #[inline]
236    fn serialize_f64(self, value: f64) -> crate::ser::Result<Bson> {
237        Ok(Bson::Double(value))
238    }
239
240    #[inline]
241    fn serialize_char(self, value: char) -> crate::ser::Result<Bson> {
242        let mut s = String::new();
243        s.push(value);
244        self.serialize_str(&s)
245    }
246
247    #[inline]
248    fn serialize_str(self, value: &str) -> crate::ser::Result<Bson> {
249        Ok(Bson::String(value.to_string()))
250    }
251
252    fn serialize_bytes(self, value: &[u8]) -> crate::ser::Result<Bson> {
253        // let mut state = self.serialize_seq(Some(value.len()))?;
254        // for byte in value {
255        //     state.serialize_element(byte)?;
256        // }
257        // state.end()
258        Ok(Bson::Binary(Binary {
259            subtype: BinarySubtype::Generic,
260            bytes: value.to_vec(),
261        }))
262    }
263
264    #[inline]
265    fn serialize_none(self) -> crate::ser::Result<Bson> {
266        self.serialize_unit()
267    }
268
269    #[inline]
270    fn serialize_some<V>(self, value: &V) -> crate::ser::Result<Bson>
271    where
272        V: Serialize + ?Sized,
273    {
274        value.serialize(self)
275    }
276
277    #[inline]
278    fn serialize_unit(self) -> crate::ser::Result<Bson> {
279        Ok(Bson::Null)
280    }
281
282    #[inline]
283    fn serialize_unit_struct(self, _name: &'static str) -> crate::ser::Result<Bson> {
284        self.serialize_unit()
285    }
286
287    #[inline]
288    fn serialize_unit_variant(
289        self,
290        _name: &'static str,
291        _variant_index: u32,
292        variant: &'static str,
293    ) -> crate::ser::Result<Bson> {
294        Ok(Bson::String(variant.to_string()))
295    }
296
297    #[inline]
298    fn serialize_newtype_struct<T>(
299        mut self,
300        name: &'static str,
301        value: &T,
302    ) -> crate::ser::Result<Bson>
303    where
304        T: Serialize + ?Sized,
305    {
306        match name {
307            UUID_NEWTYPE_NAME => {
308                let is_human_readable = self.is_human_readable();
309                match value.serialize(self)? {
310                    Bson::String(s) if is_human_readable => {
311                        // the serializer reports itself as human readable, so [`Uuid`] will
312                        // serialize itself as a string.
313                        let uuid = crate::Uuid::parse_str(s).map_err(Error::custom)?;
314                        Ok(Bson::Binary(uuid.into()))
315                    }
316                    Bson::Binary(b) if !is_human_readable => Ok(Bson::Binary(Binary {
317                        bytes: b.bytes,
318                        subtype: BinarySubtype::Uuid,
319                    })),
320                    b => {
321                        let expectation = if is_human_readable {
322                            "a string"
323                        } else {
324                            "bytes"
325                        };
326                        Err(Error::custom(format!(
327                            "expected UUID to be serialized as {} but got {:?} instead",
328                            expectation, b
329                        )))
330                    }
331                }
332            }
333            // when in non-human-readable mode, raw document / raw array will serialize as bytes.
334            RAW_DOCUMENT_NEWTYPE | RAW_ARRAY_NEWTYPE if !self.is_human_readable() => match value
335                .serialize(self)?
336            {
337                Bson::Binary(b) => {
338                    let doc = Document::from_reader(b.bytes.as_slice()).map_err(Error::custom)?;
339
340                    if name == RAW_DOCUMENT_NEWTYPE {
341                        Ok(Bson::Document(doc))
342                    } else {
343                        Ok(Bson::Array(doc.into_iter().map(|kvp| kvp.1).collect()))
344                    }
345                }
346                b => Err(Error::custom(format!(
347                    "expected raw document or array to be serialized as bytes but got {:?} instead",
348                    b
349                ))),
350            },
351            #[allow(deprecated)]
352            HUMAN_READABLE_NEWTYPE => {
353                self.options.human_readable = Some(true);
354                value.serialize(self)
355            }
356            _ => value.serialize(self),
357        }
358    }
359
360    #[inline]
361    fn serialize_newtype_variant<T>(
362        self,
363        _name: &'static str,
364        _variant_index: u32,
365        variant: &'static str,
366        value: &T,
367    ) -> crate::ser::Result<Bson>
368    where
369        T: Serialize + ?Sized,
370    {
371        let mut newtype_variant = Document::new();
372        newtype_variant.insert(variant, to_bson_with_options(value, self.options)?);
373        Ok(newtype_variant.into())
374    }
375
376    #[inline]
377    fn serialize_seq(self, len: Option<usize>) -> crate::ser::Result<Self::SerializeSeq> {
378        Ok(ArraySerializer {
379            inner: Array::with_capacity(len.unwrap_or(0)),
380            options: self.options,
381        })
382    }
383
384    #[inline]
385    fn serialize_tuple(self, len: usize) -> crate::ser::Result<Self::SerializeTuple> {
386        Ok(TupleSerializer {
387            inner: Array::with_capacity(len),
388            options: self.options,
389        })
390    }
391
392    #[inline]
393    fn serialize_tuple_struct(
394        self,
395        _name: &'static str,
396        len: usize,
397    ) -> crate::ser::Result<Self::SerializeTupleStruct> {
398        Ok(TupleStructSerializer {
399            inner: Array::with_capacity(len),
400            options: self.options,
401        })
402    }
403
404    #[inline]
405    fn serialize_tuple_variant(
406        self,
407        _name: &'static str,
408        _variant_index: u32,
409        variant: &'static str,
410        len: usize,
411    ) -> crate::ser::Result<Self::SerializeTupleVariant> {
412        Ok(TupleVariantSerializer {
413            inner: Array::with_capacity(len),
414            name: variant,
415            options: self.options,
416        })
417    }
418
419    #[inline]
420    fn serialize_map(self, _len: Option<usize>) -> crate::ser::Result<Self::SerializeMap> {
421        Ok(MapSerializer {
422            inner: Document::new(),
423            next_key: None,
424            options: self.options,
425        })
426    }
427
428    #[inline]
429    fn serialize_struct(
430        self,
431        _name: &'static str,
432        _len: usize,
433    ) -> crate::ser::Result<Self::SerializeStruct> {
434        Ok(StructSerializer {
435            inner: Document::new(),
436            options: self.options,
437        })
438    }
439
440    #[inline]
441    fn serialize_struct_variant(
442        self,
443        _name: &'static str,
444        _variant_index: u32,
445        variant: &'static str,
446        _len: usize,
447    ) -> crate::ser::Result<Self::SerializeStructVariant> {
448        Ok(StructVariantSerializer {
449            name: variant,
450            inner: Document::new(),
451            options: self.options,
452        })
453    }
454
455    #[allow(deprecated)]
456    fn is_human_readable(&self) -> bool {
457        self.options.human_readable.unwrap_or(true)
458    }
459}
460
461#[doc(hidden)]
462pub struct ArraySerializer {
463    inner: Array,
464    options: SerializerOptions,
465}
466
467impl SerializeSeq for ArraySerializer {
468    type Ok = Bson;
469    type Error = Error;
470
471    fn serialize_element<T: ?Sized + Serialize>(&mut self, value: &T) -> crate::ser::Result<()> {
472        self.inner
473            .push(to_bson_with_options(value, self.options.clone())?);
474        Ok(())
475    }
476
477    fn end(self) -> crate::ser::Result<Bson> {
478        Ok(Bson::Array(self.inner))
479    }
480}
481
482#[doc(hidden)]
483pub struct TupleSerializer {
484    inner: Array,
485    options: SerializerOptions,
486}
487
488impl SerializeTuple for TupleSerializer {
489    type Ok = Bson;
490    type Error = Error;
491
492    fn serialize_element<T: ?Sized + Serialize>(&mut self, value: &T) -> crate::ser::Result<()> {
493        self.inner
494            .push(to_bson_with_options(value, self.options.clone())?);
495        Ok(())
496    }
497
498    fn end(self) -> crate::ser::Result<Bson> {
499        Ok(Bson::Array(self.inner))
500    }
501}
502
503#[doc(hidden)]
504pub struct TupleStructSerializer {
505    inner: Array,
506    options: SerializerOptions,
507}
508
509impl SerializeTupleStruct for TupleStructSerializer {
510    type Ok = Bson;
511    type Error = Error;
512
513    fn serialize_field<T: ?Sized + Serialize>(&mut self, value: &T) -> crate::ser::Result<()> {
514        self.inner
515            .push(to_bson_with_options(value, self.options.clone())?);
516        Ok(())
517    }
518
519    fn end(self) -> crate::ser::Result<Bson> {
520        Ok(Bson::Array(self.inner))
521    }
522}
523
524#[doc(hidden)]
525pub struct TupleVariantSerializer {
526    inner: Array,
527    name: &'static str,
528    options: SerializerOptions,
529}
530
531impl SerializeTupleVariant for TupleVariantSerializer {
532    type Ok = Bson;
533    type Error = Error;
534
535    fn serialize_field<T: ?Sized + Serialize>(&mut self, value: &T) -> crate::ser::Result<()> {
536        self.inner
537            .push(to_bson_with_options(value, self.options.clone())?);
538        Ok(())
539    }
540
541    fn end(self) -> crate::ser::Result<Bson> {
542        let mut tuple_variant = Document::new();
543        tuple_variant.insert(self.name, self.inner);
544        Ok(tuple_variant.into())
545    }
546}
547
548#[doc(hidden)]
549pub struct MapSerializer {
550    inner: Document,
551    next_key: Option<String>,
552    options: SerializerOptions,
553}
554
555impl SerializeMap for MapSerializer {
556    type Ok = Bson;
557    type Error = Error;
558
559    fn serialize_key<T: ?Sized + Serialize>(&mut self, key: &T) -> crate::ser::Result<()> {
560        self.next_key = match to_bson_with_options(&key, self.options.clone())? {
561            Bson::String(s) => Some(s),
562            other => return Err(Error::InvalidDocumentKey(other)),
563        };
564        Ok(())
565    }
566
567    fn serialize_value<T: ?Sized + Serialize>(&mut self, value: &T) -> crate::ser::Result<()> {
568        let key = self.next_key.take().unwrap_or_default();
569        self.inner
570            .insert(key, to_bson_with_options(&value, self.options.clone())?);
571        Ok(())
572    }
573
574    fn end(self) -> crate::ser::Result<Bson> {
575        Ok(Bson::from_extended_document(self.inner))
576    }
577}
578
579#[doc(hidden)]
580pub struct StructSerializer {
581    inner: Document,
582    options: SerializerOptions,
583}
584
585impl SerializeStruct for StructSerializer {
586    type Ok = Bson;
587    type Error = Error;
588
589    fn serialize_field<T: ?Sized + Serialize>(
590        &mut self,
591        key: &'static str,
592        value: &T,
593    ) -> crate::ser::Result<()> {
594        self.inner
595            .insert(key, to_bson_with_options(value, self.options.clone())?);
596        Ok(())
597    }
598
599    fn end(self) -> crate::ser::Result<Bson> {
600        Ok(Bson::from_extended_document(self.inner))
601    }
602}
603
604#[doc(hidden)]
605pub struct StructVariantSerializer {
606    inner: Document,
607    name: &'static str,
608    options: SerializerOptions,
609}
610
611impl SerializeStructVariant for StructVariantSerializer {
612    type Ok = Bson;
613    type Error = Error;
614
615    fn serialize_field<T: ?Sized + Serialize>(
616        &mut self,
617        key: &'static str,
618        value: &T,
619    ) -> crate::ser::Result<()> {
620        self.inner
621            .insert(key, to_bson_with_options(value, self.options.clone())?);
622        Ok(())
623    }
624
625    fn end(self) -> crate::ser::Result<Bson> {
626        let var = Bson::from_extended_document(self.inner);
627
628        let mut struct_variant = Document::new();
629        struct_variant.insert(self.name, var);
630
631        Ok(Bson::Document(struct_variant))
632    }
633}
634
635impl Serialize for Timestamp {
636    #[inline]
637    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
638    where
639        S: ser::Serializer,
640    {
641        let mut state = serializer.serialize_struct("$timestamp", 1)?;
642        let body = extjson::models::TimestampBody {
643            t: self.time,
644            i: self.increment,
645        };
646        state.serialize_field("$timestamp", &body)?;
647        state.end()
648    }
649}
650
651impl Serialize for Regex {
652    #[inline]
653    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
654    where
655        S: ser::Serializer,
656    {
657        let raw = RawRegexRef {
658            pattern: self.pattern.as_str(),
659            options: self.options.as_str(),
660        };
661        raw.serialize(serializer)
662    }
663}
664
665impl Serialize for JavaScriptCodeWithScope {
666    #[inline]
667    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
668    where
669        S: ser::Serializer,
670    {
671        let mut state = serializer.serialize_struct("$codeWithScope", 2)?;
672        state.serialize_field("$code", &self.code)?;
673        state.serialize_field("$scope", &self.scope)?;
674        state.end()
675    }
676}
677
678impl Serialize for Binary {
679    #[inline]
680    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
681    where
682        S: ser::Serializer,
683    {
684        if let BinarySubtype::Generic = self.subtype {
685            serializer.serialize_bytes(self.bytes.as_slice())
686        } else {
687            let mut state = serializer.serialize_struct("$binary", 1)?;
688            let body = extjson::models::BinaryBody {
689                base64: base64::encode(self.bytes.as_slice()),
690                subtype: hex::encode([self.subtype.into()]),
691            };
692            state.serialize_field("$binary", &body)?;
693            state.end()
694        }
695    }
696}
697
698impl Serialize for Decimal128 {
699    #[inline]
700    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
701    where
702        S: ser::Serializer,
703    {
704        let human_readable = serializer.is_human_readable();
705        let mut state = serializer.serialize_struct("$numberDecimal", 1)?;
706        if human_readable {
707            state.serialize_field("$numberDecimal", &self.to_string())?;
708        } else {
709            state.serialize_field("$numberDecimalBytes", serde_bytes::Bytes::new(&self.bytes))?;
710        }
711        state.end()
712    }
713}
714
715impl Serialize for DateTime {
716    #[inline]
717    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
718    where
719        S: ser::Serializer,
720    {
721        let mut state = serializer.serialize_struct("$date", 1)?;
722        let body = extjson::models::DateTimeBody::from_millis(self.timestamp_millis());
723        state.serialize_field("$date", &body)?;
724        state.end()
725    }
726}
727
728impl Serialize for DbPointer {
729    #[inline]
730    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
731    where
732        S: ser::Serializer,
733    {
734        let raw = RawDbPointerRef {
735            namespace: self.namespace.as_str(),
736            id: self.id,
737        };
738        raw.serialize(serializer)
739    }
740}