num_format/
buffer.rs
1use core::borrow::Borrow;
2use core::fmt;
3use core::ops::Deref;
4use core::str;
5
6use crate::constants::MAX_BUF_LEN;
7use crate::format::Format;
8use crate::to_formatted_str::ToFormattedStr;
9
10#[derive(Copy, Clone)]
36pub struct Buffer {
37 pub(crate) inner: [u8; MAX_BUF_LEN],
38 pub(crate) pos: usize,
39 pub(crate) end: usize,
40}
41
42impl Buffer {
43 #[inline(always)]
45 pub fn new() -> Buffer {
46 Buffer {
47 inner: [0; MAX_BUF_LEN],
48 pos: MAX_BUF_LEN,
49 end: MAX_BUF_LEN,
50 }
51 }
52
53 #[inline(always)]
55 pub fn as_bytes(&self) -> &[u8] {
56 &self.inner[self.pos..self.end]
57 }
58
59 #[inline(always)]
61 pub fn as_str(&self) -> &str {
62 unsafe { str::from_utf8_unchecked(self.as_bytes()) }
63 }
64
65 #[inline(always)]
67 pub fn is_empty(&self) -> bool {
68 self.len() == 0
69 }
70
71 #[inline(always)]
73 pub fn len(&self) -> usize {
74 self.end - self.pos
75 }
76
77 #[inline(always)]
79 pub fn write_formatted<F, N>(&mut self, n: &N, format: &F) -> usize
80 where
81 F: Format,
82 N: ToFormattedStr,
83 {
84 n.read_to_buffer(self, format)
85 }
86
87 #[inline(always)]
88 pub(crate) fn as_mut_ptr(&mut self) -> *mut u8 {
89 self.inner.as_mut_ptr()
90 }
91
92 #[inline(always)]
93 pub(crate) fn write_with_itoa<N: itoa::Integer>(&mut self, n: N) -> usize {
94 let mut itoa_buf = itoa::Buffer::new();
95
96 let s = itoa_buf.format(n);
97 let s_len = s.len();
98
99 self.pos = MAX_BUF_LEN - s_len;
100 self.end = MAX_BUF_LEN;
101
102 let dst = &mut self.inner[self.pos..self.end];
103 dst.copy_from_slice(s.as_bytes());
104
105 s_len
106 }
107}
108
109impl AsRef<str> for Buffer {
110 #[inline(always)]
111 fn as_ref(&self) -> &str {
112 self.as_str()
113 }
114}
115
116impl Borrow<str> for Buffer {
117 #[inline(always)]
118 fn borrow(&self) -> &str {
119 self.as_str()
120 }
121}
122
123impl fmt::Debug for Buffer {
124 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
125 write!(f, "{}", self.as_str())
126 }
127}
128
129impl Default for Buffer {
130 #[inline(always)]
134 fn default() -> Buffer {
135 Buffer::new()
136 }
137}
138
139impl Deref for Buffer {
140 type Target = str;
141
142 #[inline(always)]
143 fn deref(&self) -> &Self::Target {
144 self.as_str()
145 }
146}
147
148impl fmt::Display for Buffer {
149 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
150 write!(f, "{}", self.as_str())
151 }
152}
153
154#[cfg(feature = "with-serde")]
155mod serialization {
156 use serde::{de, ser};
157
158 use super::*;
159
160 impl ser::Serialize for Buffer {
161 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
162 where
163 S: ser::Serializer,
164 {
165 serializer.serialize_bytes(self.as_bytes())
166 }
167 }
168
169 impl<'de> de::Deserialize<'de> for Buffer {
170 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
171 where
172 D: de::Deserializer<'de>,
173 {
174 struct BufferVisitor;
175
176 impl<'de> de::Visitor<'de> for BufferVisitor {
177 type Value = Buffer;
178
179 fn expecting(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
180 write!(f, "bytes of maximum length {}", MAX_BUF_LEN)
181 }
182
183 fn visit_seq<V>(self, mut seq: V) -> Result<Buffer, V::Error>
184 where
185 V: de::SeqAccess<'de>,
186 {
187 let mut inner: [u8; MAX_BUF_LEN] = [0; MAX_BUF_LEN];
188 let mut index = 0;
189 while let Some(value) = seq.next_element()? {
190 if index < MAX_BUF_LEN {
191 inner[index] = value;
192 index += 1;
193 } else {
194 return Err(de::Error::invalid_length(index, &self));
195 }
196 }
197 Ok(Buffer {
198 inner,
199 pos: 0,
200 end: index,
201 })
202 }
203 }
204
205 deserializer.deserialize_bytes(BufferVisitor)
206 }
207 }
208
209 #[cfg(test)]
210 mod tests {
211 use arrayvec::ArrayString;
212
213 use crate::constants::MAX_BUF_LEN;
214 use crate::{Buffer, Locale};
215
216 #[test]
217 fn test_buffer_serialization() {
218 let mut buf = Buffer::new();
219 let _ = buf.write_formatted(&1_000, &Locale::en);
220 let s = serde_json::to_string(&buf).unwrap();
221 assert_eq!(&s, "[49,44,48,48,48]");
222 }
223
224 #[test]
225 fn test_buffer_deserialization() {
226 let buf: Buffer = serde_json::from_str("[49,44,48,48,48]").unwrap();
228 assert_eq!(0, buf.pos);
229 assert_eq!(5, buf.end);
230 assert_eq!(&[49, 44, 48, 48, 48], buf.as_bytes());
231 assert_eq!("1,000", buf.as_str());
232
233 let mut should_fail = ArrayString::<1024>::new();
235 should_fail.push_str("[0");
236 for _ in 0..MAX_BUF_LEN {
237 should_fail.push_str(",0");
238 }
239 should_fail.push(']');
240 let result: Result<Buffer, serde_json::Error> = serde_json::from_str(&should_fail);
241 if result.is_ok() {
242 panic!("was somehow able to deserialize bytes that were too long")
243 }
244 }
245 }
246}