core_json_traits/
string.rs1use crate::JsonSerialize;
2
3#[cfg(feature = "alloc")]
4use crate::{Read, Stack, JsonError, Value, JsonDeserialize};
5#[cfg(feature = "alloc")]
6impl JsonDeserialize for alloc::string::String {
7 fn deserialize<'read, 'parent, B: Read<'read>, S: Stack>(
8 value: Value<'read, 'parent, B, S>,
9 ) -> Result<Self, JsonError<'read, B, S>> {
10 value.to_str()?.collect()
11 }
12}
13
14struct CharIterator<I: Iterator<Item = char>> {
15 iter: I,
16 buf: [char; 12],
17 queued: usize,
18}
19impl<I: Iterator<Item = char>> Iterator for CharIterator<I> {
20 type Item = char;
21 fn next(&mut self) -> Option<Self::Item> {
22 if self.queued == 0 {
24 let char = self.iter.next()?;
25
26 match u32::from(char) {
27 0x20 ..= 0x21 | 0x23 ..= 0x5b | 0x5d ..= 0x10ffff => {
29 self.buf[self.buf.len() - 1] = char;
30 self.queued = 1;
31 }
32 #[allow(unreachable_patterns)]
34 0x22 | 0x5c | 0x2f | 0x62 | 0x66 | 0x6e | 0x72 | 0x74 => {
35 self.buf[self.buf.len() - 2] = '\\';
36 self.buf[self.buf.len() - 1] = match u32::from(char) {
37 0x62 => 'b',
39 0x66 => 'f',
40 0x6e => 'n',
41 0x72 => 'r',
42 0x74 => 't',
43 _ => char,
45 };
46 self.queued = 2;
47 }
48 _ => {
49 let mut elems = [0; 2];
51 let elems = char.encode_utf16(&mut elems);
52 for (i, b) in elems.iter().enumerate() {
53 let i = (((2 - elems.len()) + i) * 6) + 2;
55 for n in 0 .. 4 {
57 let nibble = (((*b) >> (16 - ((n + 1) * 4))) & 0b1111) as u8;
59 self.buf[i + n] = (if let Some(value) = nibble.checked_sub(10) {
61 b'a' + value
62 } else {
63 b'0' + nibble
64 }) as char;
65 }
66 }
67 self.queued = elems.len() * 6;
68 }
69 }
70 }
71
72 let res = self.buf[12 - self.queued];
74 self.queued -= 1;
76 Some(res)
77 }
78}
79impl JsonSerialize for str {
80 fn serialize(&self) -> impl Iterator<Item = char> {
81 core::iter::once('"')
82 .chain(CharIterator {
83 iter: self.chars(),
84 buf: ['\\', 'u', 'F', 'F', 'F', 'F', '\\', 'u', 'F', 'F', 'F', 'F'],
85 queued: 0,
86 })
87 .chain(core::iter::once('"'))
88 }
89}
90
91#[cfg(feature = "alloc")]
92impl JsonSerialize for alloc::string::String {
93 fn serialize(&self) -> impl Iterator<Item = char> {
94 self.as_str().serialize()
95 }
96}