simd_json/serde/se/
pp.rs

1use crate::{Error, ErrorType, macros::stry};
2use serde_ext::ser;
3use std::io::Write;
4use std::str;
5use value_trait::generator::BaseGenerator;
6
7use super::key_must_be_a_string;
8
9macro_rules! iomap {
10    ($e:expr_2021) => {
11        ($e).map_err(|err| Error::generic(ErrorType::Io(err)))
12    };
13}
14
15/// Write a value to a vector
16/// # Errors
17/// when the data can not be written
18#[cfg_attr(not(feature = "no-inline"), inline)]
19pub fn to_vec_pretty<T>(to: &T) -> crate::Result<Vec<u8>>
20where
21    T: ser::Serialize + ?Sized,
22{
23    let v = Vec::with_capacity(512);
24    let mut s = PrettySerializer::new(v);
25    to.serialize(&mut s).map(|()| s.writer)
26}
27
28/// Write a value to a string
29///
30/// # Errors
31/// when the data can not be written
32#[cfg_attr(not(feature = "no-inline"), inline)]
33pub fn to_string_pretty<T>(to: &T) -> crate::Result<String>
34where
35    T: ser::Serialize + ?Sized,
36{
37    to_vec_pretty(to).map(|v| unsafe { String::from_utf8_unchecked(v) })
38}
39
40/// Write a value to a string
41/// # Errors
42/// when the data can not be written
43#[cfg_attr(not(feature = "no-inline"), inline)]
44pub fn to_writer_pretty<T, W>(writer: W, to: &T) -> crate::Result<()>
45where
46    T: ser::Serialize + ?Sized,
47    W: Write,
48{
49    let mut s = PrettySerializer::new(writer);
50    to.serialize(&mut s)
51}
52struct PrettySerializer<W: Write> {
53    writer: W,
54    dent: u32,
55}
56impl<W: Write> PrettySerializer<W> {
57    fn new(writer: W) -> Self {
58        Self { writer, dent: 0 }
59    }
60}
61
62impl<W> BaseGenerator for PrettySerializer<W>
63where
64    W: Write,
65{
66    type T = W;
67    #[cfg_attr(not(feature = "no-inline"), inline)]
68    fn get_writer(&mut self) -> &mut Self::T {
69        &mut self.writer
70    }
71    #[cfg_attr(not(feature = "no-inline"), inline)]
72    fn write_min(&mut self, _slice: &[u8], min: u8) -> std::io::Result<()> {
73        self.writer.write_all(&[min])
74    }
75    #[cfg_attr(not(feature = "no-inline"), inline)]
76    fn new_line(&mut self) -> std::io::Result<()> {
77        self.write_char(b'\n').and_then(|()| match self.dent {
78            0 => Ok(()),
79            1 => self.get_writer().write_all(b"  "),
80            2 => self.get_writer().write_all(b"    "),
81            3 => self.get_writer().write_all(b"      "),
82            4 => self.get_writer().write_all(b"        "),
83            5 => self.get_writer().write_all(b"          "),
84            6 => self.get_writer().write_all(b"            "),
85            7 => self.get_writer().write_all(b"              "),
86            8 => self.get_writer().write_all(b"                "),
87            9 => self.get_writer().write_all(b"                  "),
88            _ => {
89                for _ in 0..(self.dent * 2) {
90                    stry!(self.get_writer().write_all(b" "));
91                }
92                Ok(())
93            }
94        })
95    }
96
97    fn indent(&mut self) {
98        self.dent += 1;
99    }
100
101    fn dedent(&mut self) {
102        self.dent -= 1;
103    }
104}
105struct SerializeSeq<'serializer, W: Write + 'serializer> {
106    s: &'serializer mut PrettySerializer<W>,
107    first: bool,
108}
109impl<W> ser::SerializeSeq for SerializeSeq<'_, W>
110where
111    W: Write,
112{
113    type Ok = ();
114    type Error = Error;
115    #[cfg_attr(not(feature = "no-inline"), inline)]
116    fn serialize_element<T>(&mut self, value: &T) -> Result<(), Self::Error>
117    where
118        T: ?Sized + serde_ext::Serialize,
119    {
120        let SerializeSeq {
121            ref mut s,
122            ref mut first,
123            ..
124        } = *self;
125        if *first {
126            *first = false;
127            iomap!(s.new_line()).and_then(|()| value.serialize(&mut **s))
128        } else {
129            iomap!(s.write(b",").and_then(|()| s.new_line()))
130                .and_then(|()| value.serialize(&mut **s))
131        }
132    }
133    #[cfg_attr(not(feature = "no-inline"), inline)]
134    fn end(self) -> Result<Self::Ok, Self::Error> {
135        if self.first {
136            Ok(())
137        } else {
138            self.s.dedent();
139            iomap!(self.s.new_line().and_then(|()| self.s.write(b"]")))
140        }
141    }
142}
143
144impl<W> ser::SerializeTuple for SerializeSeq<'_, W>
145where
146    W: Write,
147{
148    type Ok = ();
149    type Error = Error;
150    #[cfg_attr(not(feature = "no-inline"), inline)]
151    fn serialize_element<T>(&mut self, value: &T) -> Result<(), Self::Error>
152    where
153        T: ?Sized + serde_ext::Serialize,
154    {
155        let SerializeSeq {
156            ref mut s,
157            ref mut first,
158        } = *self;
159        if *first {
160            *first = false;
161            iomap!(s.new_line()).and_then(|()| value.serialize(&mut **s))
162        } else {
163            iomap!(s.write(b",").and_then(|()| s.new_line()))
164                .and_then(|()| value.serialize(&mut **s))
165        }
166    }
167    #[cfg_attr(not(feature = "no-inline"), inline)]
168    fn end(self) -> Result<Self::Ok, Self::Error> {
169        if self.first {
170            Ok(())
171        } else {
172            self.s.dedent();
173            iomap!(self.s.new_line().and_then(|()| self.s.write(b"]")))
174        }
175    }
176}
177
178impl<W> ser::SerializeTupleStruct for SerializeSeq<'_, W>
179where
180    W: Write,
181{
182    type Ok = ();
183    type Error = Error;
184    #[cfg_attr(not(feature = "no-inline"), inline)]
185    fn serialize_field<T>(&mut self, value: &T) -> Result<(), Self::Error>
186    where
187        T: ?Sized + serde_ext::Serialize,
188    {
189        let SerializeSeq {
190            ref mut s,
191            ref mut first,
192        } = *self;
193        if *first {
194            *first = false;
195            iomap!(s.new_line()).and_then(|()| value.serialize(&mut **s))
196        } else {
197            iomap!(s.write(b",").and_then(|()| s.new_line()))
198                .and_then(|()| value.serialize(&mut **s))
199        }
200    }
201    #[cfg_attr(not(feature = "no-inline"), inline)]
202    fn end(self) -> Result<Self::Ok, Self::Error> {
203        if self.first {
204            Ok(())
205        } else {
206            self.s.dedent();
207            iomap!(self.s.new_line().and_then(|()| self.s.write(b"]")))
208        }
209    }
210}
211
212impl<W> ser::SerializeTupleVariant for SerializeSeq<'_, W>
213where
214    W: Write,
215{
216    type Ok = ();
217    type Error = Error;
218    #[cfg_attr(not(feature = "no-inline"), inline)]
219    fn serialize_field<T>(&mut self, value: &T) -> Result<(), Self::Error>
220    where
221        T: ?Sized + serde_ext::Serialize,
222    {
223        let SerializeSeq {
224            ref mut s,
225            ref mut first,
226        } = *self;
227        if *first {
228            *first = false;
229            iomap!(s.new_line()).and_then(|()| value.serialize(&mut **s))
230        } else {
231            iomap!(s.write(b",").and_then(|()| s.new_line()))
232                .and_then(|()| value.serialize(&mut **s))
233        }
234    }
235    #[cfg_attr(not(feature = "no-inline"), inline)]
236    fn end(self) -> Result<Self::Ok, Self::Error> {
237        if self.first {
238            Ok(())
239        } else {
240            self.s.dedent();
241            iomap!(self.s.new_line().and_then(|()| self.s.write(b"}")))
242        }
243    }
244}
245
246struct MapKeySerializer<'serializer, W: Write + 'serializer> {
247    s: &'serializer mut PrettySerializer<W>,
248}
249
250impl<W> ser::Serializer for MapKeySerializer<'_, W>
251where
252    W: Write,
253{
254    type Ok = ();
255    type Error = Error;
256
257    #[cfg_attr(not(feature = "no-inline"), inline)]
258    fn serialize_str(self, value: &str) -> Result<(), Self::Error> {
259        self.s.serialize_str(value)
260    }
261
262    #[cfg_attr(not(feature = "no-inline"), inline)]
263    fn serialize_unit_variant(
264        self,
265        _name: &'static str,
266        _variant_index: u32,
267        variant: &'static str,
268    ) -> Result<(), Self::Error> {
269        self.s.serialize_str(variant)
270    }
271
272    #[cfg_attr(not(feature = "no-inline"), inline)]
273    fn serialize_newtype_struct<T>(self, _name: &'static str, value: &T) -> Result<(), Self::Error>
274    where
275        T: ?Sized + serde_ext::Serialize,
276    {
277        value.serialize(self)
278    }
279
280    type SerializeSeq = ser::Impossible<(), Error>;
281    type SerializeTuple = ser::Impossible<(), Error>;
282    type SerializeTupleStruct = ser::Impossible<(), Error>;
283    type SerializeTupleVariant = ser::Impossible<(), Error>;
284    type SerializeMap = ser::Impossible<(), Error>;
285    type SerializeStruct = ser::Impossible<(), Error>;
286    type SerializeStructVariant = ser::Impossible<(), Error>;
287
288    fn serialize_bool(self, _value: bool) -> Result<(), Self::Error> {
289        Err(key_must_be_a_string())
290    }
291
292    fn serialize_i8(self, v: i8) -> Result<Self::Ok, Self::Error> {
293        iomap!(
294            self.s
295                .write_char(b'"')
296                .and_then(|()| self.s.write_int(v))
297                .and_then(|()| self.s.write_char(b'"'))
298        )
299    }
300
301    fn serialize_i16(self, v: i16) -> Result<Self::Ok, Self::Error> {
302        iomap!(
303            self.s
304                .write_char(b'"')
305                .and_then(|()| self.s.write_int(v))
306                .and_then(|()| self.s.write_char(b'"'))
307        )
308    }
309
310    fn serialize_i32(self, v: i32) -> Result<Self::Ok, Self::Error> {
311        iomap!(
312            self.s
313                .write_char(b'"')
314                .and_then(|()| self.s.write_int(v))
315                .and_then(|()| self.s.write_char(b'"'))
316        )
317    }
318
319    fn serialize_i64(self, v: i64) -> Result<Self::Ok, Self::Error> {
320        iomap!(
321            self.s
322                .write_char(b'"')
323                .and_then(|()| self.s.write_int(v))
324                .and_then(|()| self.s.write_char(b'"'))
325        )
326    }
327
328    fn serialize_i128(self, v: i128) -> Result<Self::Ok, Self::Error> {
329        iomap!(
330            self.s
331                .write_char(b'"')
332                .and_then(|()| self.s.write_int(v))
333                .and_then(|()| self.s.write_char(b'"'))
334        )
335    }
336
337    fn serialize_u8(self, v: u8) -> Result<Self::Ok, Self::Error> {
338        iomap!(
339            self.s
340                .write_char(b'"')
341                .and_then(|()| self.s.write_int(v))
342                .and_then(|()| self.s.write_char(b'"'))
343        )
344    }
345
346    fn serialize_u16(self, v: u16) -> Result<Self::Ok, Self::Error> {
347        iomap!(
348            self.s
349                .write_char(b'"')
350                .and_then(|()| self.s.write_int(v))
351                .and_then(|()| self.s.write_char(b'"'))
352        )
353    }
354
355    fn serialize_u32(self, v: u32) -> Result<Self::Ok, Self::Error> {
356        iomap!(
357            self.s
358                .write_char(b'"')
359                .and_then(|()| self.s.write_int(v))
360                .and_then(|()| self.s.write_char(b'"'))
361        )
362    }
363
364    fn serialize_u64(self, v: u64) -> Result<Self::Ok, Self::Error> {
365        iomap!(
366            self.s
367                .write_char(b'"')
368                .and_then(|()| self.s.write_int(v))
369                .and_then(|()| self.s.write_char(b'"'))
370        )
371    }
372
373    fn serialize_u128(self, v: u128) -> Result<Self::Ok, Self::Error> {
374        iomap!(
375            self.s
376                .write_char(b'"')
377                .and_then(|()| self.s.write_int(v))
378                .and_then(|()| self.s.write_char(b'"'))
379        )
380    }
381
382    fn serialize_f32(self, _v: f32) -> Result<Self::Ok, Self::Error> {
383        Err(key_must_be_a_string())
384    }
385
386    fn serialize_f64(self, _v: f64) -> Result<Self::Ok, Self::Error> {
387        Err(key_must_be_a_string())
388    }
389
390    fn serialize_char(self, v: char) -> Result<Self::Ok, Self::Error> {
391        self.s.serialize_str(&v.to_string())
392    }
393
394    fn serialize_bytes(self, _v: &[u8]) -> Result<Self::Ok, Self::Error> {
395        Err(key_must_be_a_string())
396    }
397
398    fn serialize_none(self) -> Result<Self::Ok, Self::Error> {
399        Err(key_must_be_a_string())
400    }
401
402    fn serialize_some<T>(self, _value: &T) -> Result<Self::Ok, Self::Error>
403    where
404        T: ?Sized + serde_ext::Serialize,
405    {
406        Err(key_must_be_a_string())
407    }
408
409    fn serialize_unit(self) -> Result<Self::Ok, Self::Error> {
410        Err(key_must_be_a_string())
411    }
412
413    fn serialize_unit_struct(self, _name: &'static str) -> Result<Self::Ok, Self::Error> {
414        Err(key_must_be_a_string())
415    }
416
417    fn serialize_newtype_variant<T>(
418        self,
419        _name: &'static str,
420        _variant_index: u32,
421        _variant: &'static str,
422        _value: &T,
423    ) -> Result<Self::Ok, Self::Error>
424    where
425        T: ?Sized + serde_ext::Serialize,
426    {
427        Err(key_must_be_a_string())
428    }
429
430    fn serialize_seq(self, _len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
431        Err(key_must_be_a_string())
432    }
433
434    fn serialize_tuple(self, _len: usize) -> Result<Self::SerializeTuple, Self::Error> {
435        Err(key_must_be_a_string())
436    }
437
438    fn serialize_tuple_struct(
439        self,
440        _name: &'static str,
441        _len: usize,
442    ) -> Result<Self::SerializeTupleStruct, Self::Error> {
443        Err(key_must_be_a_string())
444    }
445
446    fn serialize_tuple_variant(
447        self,
448        _name: &'static str,
449        _variant_index: u32,
450        _variant: &'static str,
451        _len: usize,
452    ) -> Result<Self::SerializeTupleVariant, Self::Error> {
453        Err(key_must_be_a_string())
454    }
455
456    fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
457        Err(key_must_be_a_string())
458    }
459
460    fn serialize_struct(
461        self,
462        _name: &'static str,
463        _len: usize,
464    ) -> Result<Self::SerializeStruct, Self::Error> {
465        Err(key_must_be_a_string())
466    }
467
468    fn serialize_struct_variant(
469        self,
470        _name: &'static str,
471        _variant_index: u32,
472        _variant: &'static str,
473        _len: usize,
474    ) -> Result<Self::SerializeStructVariant, Self::Error> {
475        Err(key_must_be_a_string())
476    }
477}
478
479struct SerializeMap<'serializer, W: Write + 'serializer> {
480    s: &'serializer mut PrettySerializer<W>,
481    first: bool,
482}
483
484impl<W> ser::SerializeMap for SerializeMap<'_, W>
485where
486    W: Write,
487{
488    type Ok = ();
489    type Error = Error;
490    #[cfg_attr(not(feature = "no-inline"), inline)]
491    fn serialize_key<T>(&mut self, key: &T) -> Result<(), Self::Error>
492    where
493        T: ?Sized + serde_ext::Serialize,
494    {
495        let SerializeMap {
496            ref mut s,
497            ref mut first,
498            ..
499        } = *self;
500
501        if *first {
502            *first = false;
503            iomap!(s.new_line())
504                .and_then(|()| key.serialize(MapKeySerializer { s: &mut **s }))
505                .and_then(|()| iomap!(s.write(b": ")))
506        } else {
507            iomap!(s.write(b",").and_then(|()| s.new_line()))
508                .and_then(|()| key.serialize(MapKeySerializer { s: &mut **s }))
509                .and_then(|()| iomap!(s.write(b": ")))
510        }
511    }
512    #[cfg_attr(not(feature = "no-inline"), inline)]
513    fn serialize_value<T>(&mut self, value: &T) -> Result<(), Self::Error>
514    where
515        T: ?Sized + serde_ext::Serialize,
516    {
517        let SerializeMap { ref mut s, .. } = *self;
518        value.serialize(&mut **s)
519    }
520    #[cfg_attr(not(feature = "no-inline"), inline)]
521    fn end(self) -> Result<Self::Ok, Self::Error> {
522        if self.first {
523            Ok(())
524        } else {
525            self.s.dedent();
526            iomap!(self.s.new_line().and_then(|()| self.s.write(b"}")))
527        }
528    }
529}
530
531impl<W> ser::SerializeStruct for SerializeMap<'_, W>
532where
533    W: Write,
534{
535    type Ok = ();
536    type Error = Error;
537    #[cfg_attr(not(feature = "no-inline"), inline)]
538    fn serialize_field<T>(&mut self, key: &'static str, value: &T) -> Result<(), Self::Error>
539    where
540        T: ?Sized + serde_ext::Serialize,
541    {
542        let SerializeMap {
543            ref mut s,
544            ref mut first,
545            ..
546        } = *self;
547        if *first {
548            *first = false;
549            iomap!(
550                s.new_line()
551                    .and_then(|()| s.write_simple_string(key))
552                    .and_then(|()| s.write(b": "))
553            )
554            .and_then(|()| value.serialize(&mut **s))
555        } else {
556            iomap!(
557                s.write(b",")
558                    .and_then(|()| s.write_simple_string(key))
559                    .and_then(|()| s.write(b": "))
560            )
561            .and_then(|()| value.serialize(&mut **s))
562        }
563    }
564    #[cfg_attr(not(feature = "no-inline"), inline)]
565    fn end(self) -> Result<Self::Ok, Self::Error> {
566        if self.first {
567            Ok(())
568        } else {
569            self.s.dedent();
570            iomap!(self.s.new_line().and_then(|()| self.s.write(b"}")))
571        }
572    }
573}
574
575struct SerializeStructVariant<'serializer, W: Write + 'serializer> {
576    s: &'serializer mut PrettySerializer<W>,
577    first: bool,
578}
579
580impl<W> ser::SerializeStructVariant for SerializeStructVariant<'_, W>
581where
582    W: Write,
583{
584    type Ok = ();
585    type Error = Error;
586    #[cfg_attr(not(feature = "no-inline"), inline)]
587    fn serialize_field<T>(&mut self, key: &'static str, value: &T) -> Result<(), Self::Error>
588    where
589        T: ?Sized + serde_ext::Serialize,
590    {
591        let SerializeStructVariant {
592            ref mut s,
593            ref mut first,
594            ..
595        } = *self;
596        if *first {
597            *first = false;
598            s.indent();
599            iomap!(
600                s.new_line()
601                    .and_then(|()| s.write_simple_string(key))
602                    .and_then(|()| s.write(b": "))
603            )
604            .and_then(|()| value.serialize(&mut **s))
605        } else {
606            iomap!(
607                s.write(b",")
608                    .and_then(|()| s.write_simple_string(key))
609                    .and_then(|()| s.write(b": "))
610            )
611            .and_then(|()| value.serialize(&mut **s))
612        }
613    }
614    #[cfg_attr(not(feature = "no-inline"), inline)]
615    fn end(self) -> Result<Self::Ok, Self::Error> {
616        self.s.dedent();
617        iomap!(self.s.new_line().and_then(|()| self.s.write(b"}"))).and_then(move |()| {
618            if self.first {
619                Ok(())
620            } else {
621                self.s.dedent();
622
623                iomap!(self.s.new_line().and_then(|()| self.s.write(b"}")))
624            }
625        })
626    }
627}
628
629impl<'writer, W> ser::Serializer for &'writer mut PrettySerializer<W>
630where
631    W: Write,
632{
633    type Ok = ();
634    type Error = Error;
635    type SerializeSeq = SerializeSeq<'writer, W>;
636    type SerializeTuple = SerializeSeq<'writer, W>;
637    type SerializeTupleStruct = SerializeSeq<'writer, W>;
638    type SerializeTupleVariant = SerializeSeq<'writer, W>;
639    type SerializeMap = SerializeMap<'writer, W>;
640    type SerializeStruct = SerializeMap<'writer, W>;
641    type SerializeStructVariant = SerializeStructVariant<'writer, W>;
642    #[cfg_attr(not(feature = "no-inline"), inline)]
643    fn serialize_bool(self, v: bool) -> Result<Self::Ok, Self::Error> {
644        if v {
645            iomap!(self.write(b"true"))
646        } else {
647            iomap!(self.write(b"false"))
648        }
649    }
650    #[cfg_attr(not(feature = "no-inline"), inline)]
651    fn serialize_i8(self, v: i8) -> Result<Self::Ok, Self::Error> {
652        iomap!(self.write_int(v))
653    }
654    #[cfg_attr(not(feature = "no-inline"), inline)]
655    fn serialize_i16(self, v: i16) -> Result<Self::Ok, Self::Error> {
656        iomap!(self.write_int(v))
657    }
658    #[cfg_attr(not(feature = "no-inline"), inline)]
659    fn serialize_i32(self, v: i32) -> Result<Self::Ok, Self::Error> {
660        iomap!(self.write_int(v))
661    }
662    #[cfg_attr(not(feature = "no-inline"), inline)]
663    fn serialize_i64(self, v: i64) -> Result<Self::Ok, Self::Error> {
664        iomap!(self.write_int(v))
665    }
666    #[cfg_attr(not(feature = "no-inline"), inline)]
667    fn serialize_i128(self, v: i128) -> Result<Self::Ok, Self::Error> {
668        iomap!(self.write_int(v))
669    }
670    #[cfg_attr(not(feature = "no-inline"), inline)]
671    fn serialize_u8(self, v: u8) -> Result<Self::Ok, Self::Error> {
672        iomap!(self.write_int(v))
673    }
674    #[cfg_attr(not(feature = "no-inline"), inline)]
675    fn serialize_u16(self, v: u16) -> Result<Self::Ok, Self::Error> {
676        iomap!(self.write_int(v))
677    }
678    #[cfg_attr(not(feature = "no-inline"), inline)]
679    fn serialize_u32(self, v: u32) -> Result<Self::Ok, Self::Error> {
680        iomap!(self.write_int(v))
681    }
682    #[cfg_attr(not(feature = "no-inline"), inline)]
683    fn serialize_u64(self, v: u64) -> Result<Self::Ok, Self::Error> {
684        iomap!(self.write_int(v))
685    }
686    #[cfg_attr(not(feature = "no-inline"), inline)]
687    fn serialize_u128(self, v: u128) -> Result<Self::Ok, Self::Error> {
688        iomap!(self.write_int(v))
689    }
690
691    #[cfg_attr(not(feature = "no-inline"), inline)]
692    fn serialize_f32(self, v: f32) -> Result<Self::Ok, Self::Error> {
693        iomap!(self.write_float(f64::from(v)))
694    }
695    #[cfg_attr(not(feature = "no-inline"), inline)]
696    fn serialize_f64(self, v: f64) -> Result<Self::Ok, Self::Error> {
697        iomap!(self.write_float(v))
698    }
699    #[cfg_attr(not(feature = "no-inline"), inline)]
700    fn serialize_char(self, v: char) -> Result<Self::Ok, Self::Error> {
701        // A char encoded as UTF-8 takes 4 bytes at most.
702        // taken from: https://docs.serde.rs/src/serde_json/ser.rs.html#213
703        let mut buf = [0; 4];
704        iomap!(self.write_simple_string(v.encode_utf8(&mut buf)))
705    }
706    #[cfg_attr(not(feature = "no-inline"), inline)]
707    fn serialize_str(self, v: &str) -> Result<Self::Ok, Self::Error> {
708        iomap!(self.write_string(v))
709    }
710    #[cfg_attr(not(feature = "no-inline"), inline)]
711    fn serialize_bytes(self, v: &[u8]) -> Result<Self::Ok, Self::Error> {
712        iomap!(self.write(b"[").and_then(|()| {
713            if let Some((first, rest)) = v.split_first() {
714                self.indent();
715                self.new_line().and_then(|()| {
716                    self.write_int(*first).and_then(|()| {
717                        for v in rest {
718                            self.write(b",").and_then(|()| self.write_int(*v))?;
719                        }
720                        self.dedent();
721                        self.new_line().and_then(|()| self.write(b"]"))
722                    })
723                })
724            } else {
725                self.write(b"]")
726            }
727        }))
728    }
729    #[cfg_attr(not(feature = "no-inline"), inline)]
730    fn serialize_none(self) -> Result<Self::Ok, Self::Error> {
731        self.serialize_unit()
732    }
733    #[cfg_attr(not(feature = "no-inline"), inline)]
734    fn serialize_some<T>(self, value: &T) -> Result<Self::Ok, Self::Error>
735    where
736        T: ?Sized + serde_ext::Serialize,
737    {
738        value.serialize(self)
739    }
740    #[cfg_attr(not(feature = "no-inline"), inline)]
741    fn serialize_unit(self) -> Result<Self::Ok, Self::Error> {
742        iomap!(self.write(b"null"))
743    }
744    #[cfg_attr(not(feature = "no-inline"), inline)]
745    fn serialize_unit_struct(self, _name: &'static str) -> Result<Self::Ok, Self::Error> {
746        self.serialize_unit()
747    }
748    #[cfg_attr(not(feature = "no-inline"), inline)]
749    fn serialize_unit_variant(
750        self,
751        _name: &'static str,
752        _variant_index: u32,
753        variant: &'static str,
754    ) -> Result<Self::Ok, Self::Error> {
755        iomap!(self.write_simple_string(variant))
756    }
757
758    #[cfg_attr(not(feature = "no-inline"), inline)]
759    fn serialize_newtype_struct<T>(
760        self,
761        _name: &'static str,
762        value: &T,
763    ) -> Result<Self::Ok, Self::Error>
764    where
765        T: ?Sized + serde_ext::Serialize,
766    {
767        value.serialize(self)
768    }
769
770    #[cfg_attr(not(feature = "no-inline"), inline)]
771    fn serialize_newtype_variant<T>(
772        self,
773        _name: &'static str,
774        _variant_index: u32,
775        variant: &'static str,
776        value: &T,
777    ) -> Result<Self::Ok, Self::Error>
778    where
779        T: ?Sized + serde_ext::Serialize,
780    {
781        iomap!(
782            self.write(b"{")
783                .and_then(|()| self.write_simple_string(variant))
784                .and_then(|()| self.write(b": "))
785        )
786        .and_then(|()| value.serialize(&mut *self))
787        .and_then(|()| iomap!(self.write(b"}")))
788    }
789    #[cfg_attr(not(feature = "no-inline"), inline)]
790    fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
791        if len == Some(0) {
792            iomap!(self.write(b"[]"))
793        } else {
794            self.indent();
795            iomap!(self.write(b"["))
796        }
797        .map(move |()| SerializeSeq {
798            s: self,
799            first: true,
800        })
801    }
802
803    #[cfg_attr(not(feature = "no-inline"), inline)]
804    fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> {
805        self.serialize_seq(Some(len))
806    }
807
808    #[cfg_attr(not(feature = "no-inline"), inline)]
809    fn serialize_tuple_struct(
810        self,
811        _name: &'static str,
812        len: usize,
813    ) -> Result<Self::SerializeTupleStruct, Self::Error> {
814        self.serialize_seq(Some(len))
815    }
816
817    #[cfg_attr(not(feature = "no-inline"), inline)]
818    fn serialize_tuple_variant(
819        self,
820        _name: &'static str,
821        _variant_index: u32,
822        variant: &'static str,
823        len: usize,
824    ) -> Result<Self::SerializeTupleVariant, Self::Error> {
825        self.indent();
826        iomap!(
827            self.write(b"{")
828                .and_then(|()| self.new_line())
829                .and_then(|()| self.write_simple_string(variant))
830                .and_then(|()| self.write(b": "))
831        )
832        .and_then(move |()| self.serialize_seq(Some(len)))
833    }
834
835    #[cfg_attr(not(feature = "no-inline"), inline)]
836    fn serialize_map(self, len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
837        if len == Some(0) {
838            iomap!(self.write(b"{}"))
839        } else {
840            self.indent();
841            iomap!(self.write(b"{"))
842        }
843        .map(move |()| SerializeMap {
844            s: self,
845            first: true,
846        })
847    }
848
849    #[cfg_attr(not(feature = "no-inline"), inline)]
850    fn serialize_struct(
851        self,
852        _name: &'static str,
853        len: usize,
854    ) -> Result<Self::SerializeStruct, Self::Error> {
855        self.serialize_map(Some(len))
856    }
857
858    #[cfg_attr(not(feature = "no-inline"), inline)]
859    fn serialize_struct_variant(
860        self,
861        _name: &'static str,
862        _variant_index: u32,
863        variant: &'static str,
864        len: usize,
865    ) -> Result<Self::SerializeStructVariant, Self::Error> {
866        self.indent();
867        iomap!(
868            self.write(b"{")
869                .and_then(|()| self.new_line())
870                .and_then(|()| self.write_simple_string(variant))
871                .and_then(|()| self.write(b": "))
872        )
873        .and_then(move |()| {
874            if len == 0 {
875                iomap!(self.write(b"{}"))
876            } else {
877                iomap!(self.write(b"{"))
878            }
879            .map(move |()| SerializeStructVariant {
880                s: self,
881                first: true,
882            })
883        })
884    }
885}
886
887#[cfg(test)]
888mod test {
889    #![allow(clippy::ignored_unit_patterns, unused_imports)]
890    use crate::OwnedValue as Value;
891    #[cfg(not(target_arch = "wasm32"))]
892    use crate::StaticNode;
893    use crate::from_slice;
894    #[cfg(not(target_arch = "wasm32"))]
895    use proptest::prelude::*;
896    #[test]
897    fn pretty_print_serde() {
898        #[derive(Clone, Debug, PartialEq, serde::Serialize)]
899        enum Segment {
900            Id { mid: usize },
901        }
902
903        assert_eq!(
904            "{\n  \"Id\": {\n    \"mid\": 0\n  }\n}",
905            crate::to_string_pretty(&Segment::Id { mid: 0 }).expect("to_string_pretty")
906        );
907    }
908
909    #[test]
910    fn numerical_map_serde() {
911        use std::collections::HashMap;
912
913        #[derive(Clone, Debug, PartialEq, serde::Serialize)]
914        struct Foo {
915            pub bar: HashMap<i32, i32>,
916        }
917
918        let mut foo = Foo {
919            bar: HashMap::new(),
920        };
921
922        foo.bar.insert(1337, 1337);
923
924        assert_eq!(
925            r#"{
926  "bar": {
927    "1337": 1337
928  }
929}"#,
930            crate::to_string_pretty(&foo).expect("to_string_pretty")
931        );
932    }
933
934    #[cfg(not(feature = "128bit"))]
935    #[cfg(not(target_arch = "wasm32"))]
936    fn arb_json_value() -> BoxedStrategy<Value> {
937        let leaf = prop_oneof![
938            Just(Value::Static(StaticNode::Null)),
939            any::<bool>().prop_map(Value::from),
940            //(-1.0e306f64..1.0e306f64).prop_map(Value::from), // damn you float!
941            any::<i8>().prop_map(Value::from),
942            any::<i16>().prop_map(Value::from),
943            any::<i32>().prop_map(Value::from),
944            any::<i64>().prop_map(Value::from),
945            any::<u8>().prop_map(Value::from),
946            any::<u16>().prop_map(Value::from),
947            any::<u32>().prop_map(Value::from),
948            any::<u64>().prop_map(Value::from),
949            ".*".prop_map(Value::from),
950        ];
951        leaf.prop_recursive(
952            8,   // 8 levels deep
953            256, // Shoot for maximum size of 256 nodes
954            10,  // We put up to 10 items per collection
955            |inner| {
956                prop_oneof![
957                    // Take the inner strategy and make the two recursive cases.
958                    prop::collection::vec(inner.clone(), 0..10).prop_map(Value::from),
959                    prop::collection::hash_map(".*", inner, 0..10).prop_map(Value::from),
960                ]
961            },
962        )
963        .boxed()
964    }
965
966    #[cfg(feature = "128bit")]
967    #[cfg(not(target_arch = "wasm32"))]
968    fn arb_json_value() -> BoxedStrategy<Value> {
969        let leaf = prop_oneof![
970            Just(Value::Static(StaticNode::Null)),
971            any::<bool>().prop_map(Value::from),
972            //(-1.0e306f64..1.0e306f64).prop_map(Value::from), // damn you float!
973            any::<i8>().prop_map(Value::from),
974            any::<i16>().prop_map(Value::from),
975            any::<i32>().prop_map(Value::from),
976            any::<i64>().prop_map(Value::from),
977            any::<u8>().prop_map(Value::from),
978            any::<u16>().prop_map(Value::from),
979            any::<u32>().prop_map(Value::from),
980            any::<u64>().prop_map(Value::from),
981            any::<i128>().prop_map(Value::from),
982            any::<u128>().prop_map(Value::from),
983            ".*".prop_map(Value::from),
984        ];
985        leaf.prop_recursive(
986            8,   // 8 levels deep
987            256, // Shoot for maximum size of 256 nodes
988            10,  // We put up to 10 items per collection
989            |inner| {
990                prop_oneof![
991                    // Take the inner strategy and make the two recursive cases.
992                    prop::collection::vec(inner.clone(), 0..10).prop_map(Value::from),
993                    prop::collection::hash_map(".*", inner, 0..10).prop_map(Value::from),
994                ]
995            },
996        )
997        .boxed()
998    }
999
1000    #[cfg(not(target_arch = "wasm32"))]
1001    proptest! {
1002        #![proptest_config(ProptestConfig {
1003            // Setting both fork and timeout is redundant since timeout implies
1004            // fork, but both are shown for clarity.
1005            // Disabled for code coverage, enable to track bugs
1006            // fork: true,
1007            .. ProptestConfig::default()
1008        })]
1009
1010        #[test]
1011        fn prop_json_encode_decode(val in arb_json_value()) {
1012            let mut encoded = crate::to_vec_pretty(&val).expect("to_vec_pretty");
1013            println!("{}", String::from_utf8_lossy(&encoded.clone()));
1014            let res: Value = crate::from_slice(encoded.as_mut_slice()).expect("can't convert");
1015            assert_eq!(val, res);
1016        }
1017        #[test]
1018        fn prop_serd_compat(val in arb_json_value()) {
1019            let simd = crate::to_string_pretty(&val).expect("to_string_pretty");
1020            let serde = serde_json::to_string_pretty(&val).expect("to_string_pretty");
1021            assert_eq!(simd, serde);
1022        }
1023    }
1024
1025    #[test]
1026    fn prettyfy() {
1027        let v = crate::json!({"key1":{}, "key2":[], "key3":[1,{"key4":null}]});
1028        let mut res = match crate::to_vec_pretty(&v) {
1029            Ok(res) => res,
1030            Err(e) => {
1031                println!("prettify: {e}");
1032                assert_eq!(v, "snot");
1033                vec![]
1034            }
1035        };
1036        let s = unsafe { String::from_utf8_unchecked(res.clone()) };
1037        println!("{s}");
1038        let v2: Value = from_slice(&mut res).expect("generated bad json");
1039        assert_eq!(v, v2);
1040    }
1041}