1use keyvalues_parser::Vdf;
4use serde_core::{ser, Serialize};
5
6use std::io::Write;
7
8use crate::{
9 error::{Error, Result},
10 tokens::{NaiveToken, NaiveTokenStream},
11};
12
13#[derive(Default)]
18pub struct Serializer {
19 tokens: NaiveTokenStream,
20}
21
22impl Serializer {
23 pub fn new() -> Self {
25 Self::default()
26 }
27}
28
29pub fn to_writer<W, T>(writer: &mut W, value: &T) -> Result<()>
35where
36 W: Write,
37 T: Serialize,
38{
39 _to_writer(writer, value, None)
40}
41
42pub fn to_writer_with_key<W, T>(writer: &mut W, value: &T, key: &str) -> Result<()>
48where
49 W: Write,
50 T: Serialize,
51{
52 _to_writer(writer, value, Some(key))
53}
54
55fn _to_writer<W, T>(writer: &mut W, value: &T, maybe_key: Option<&str>) -> Result<()>
63where
64 W: Write,
65 T: Serialize,
66{
67 let mut serializer = Serializer::new();
68 value.serialize(&mut serializer)?;
69
70 if let Some(key) = maybe_key {
71 match serializer.tokens.first() {
72 Some(NaiveToken::Str(_old_key)) => {
74 serializer.tokens[0] = NaiveToken::Str(key.to_owned());
75 }
76 Some(_) => serializer.tokens.insert(0, NaiveToken::Str(key.to_owned())),
78 None => {}
79 }
80 }
81
82 let vdf = Vdf::try_from(&serializer.tokens)?;
83 write!(writer, "{vdf}")?;
84
85 Ok(())
86}
87
88pub fn to_string<T>(value: &T) -> Result<String>
94where
95 T: Serialize,
96{
97 let mut buffer = Vec::new();
98 to_writer(&mut buffer, value)?;
99 let s = String::from_utf8(buffer).expect("Input was all valid UTF-8");
100
101 Ok(s)
102}
103
104pub fn to_string_with_key<T>(value: &T, key: &str) -> Result<String>
110where
111 T: Serialize,
112{
113 let mut buffer = Vec::new();
114 to_writer_with_key(&mut buffer, value, key)?;
115 let s = String::from_utf8(buffer).expect("Input was all valid UTF-8");
116
117 Ok(s)
118}
119
120macro_rules! forward_serialize_as_str {
121 ( $( ( $method:ident, $ty:ty ) ),* $(,)? ) => {
122 $(
123 fn $method(self, v: $ty) -> Result<()> {
124 self.serialize_str(&v.to_string())
125 }
126 )*
127 }
128}
129
130impl ser::Serializer for &mut Serializer {
131 type Ok = ();
132
133 type Error = Error;
134
135 type SerializeSeq = Self;
136 type SerializeTuple = Self;
137 type SerializeTupleStruct = Self;
138 type SerializeTupleVariant = Self;
139 type SerializeMap = Self;
140 type SerializeStruct = Self;
141 type SerializeStructVariant = Self;
142
143 forward_serialize_as_str!(
144 (serialize_i8, i8),
145 (serialize_i16, i16),
146 (serialize_i32, i32),
147 (serialize_i64, i64),
148 (serialize_i128, i128),
149 (serialize_u8, u8),
150 (serialize_u16, u16),
151 (serialize_u32, u32),
152 (serialize_u64, u64),
153 (serialize_u128, u128),
154 (serialize_char, char),
155 );
156
157 fn serialize_str(self, v: &str) -> Result<()> {
158 self.tokens.push(NaiveToken::str(v));
159 Ok(())
160 }
161
162 fn serialize_bool(self, v: bool) -> Result<()> {
163 self.serialize_i8(v as i8)
164 }
165
166 fn serialize_f32(self, v: f32) -> Result<()> {
167 if v.is_finite() {
168 self.serialize_str(&v.to_string())
169 } else {
170 Err(Error::NonFiniteFloat(v))
171 }
172 }
173
174 fn serialize_f64(self, v: f64) -> Result<()> {
175 self.serialize_f32(v as f32)
180 }
181
182 fn serialize_bytes(self, _v: &[u8]) -> Result<()> {
183 Err(Error::Unsupported("Bytes"))
184 }
185
186 fn serialize_none(self) -> Result<()> {
187 self.tokens.push(NaiveToken::Null);
188 Ok(())
189 }
190
191 fn serialize_some<T>(self, value: &T) -> Result<()>
192 where
193 T: ?Sized + Serialize,
194 {
195 value.serialize(self)
197 }
198
199 fn serialize_unit(self) -> Result<()> {
200 Err(Error::Unsupported("Unit Type"))
201 }
202
203 fn serialize_unit_struct(self, _name: &'static str) -> Result<()> {
204 Err(Error::Unsupported("Unit Struct"))
205 }
206
207 fn serialize_unit_variant(
208 self,
209 _name: &'static str,
210 _variant_index: u32,
211 variant: &'static str,
212 ) -> Result<()> {
213 self.serialize_str(variant)
215 }
216
217 fn serialize_newtype_struct<T>(self, _name: &'static str, value: &T) -> Result<()>
218 where
219 T: ?Sized + Serialize,
220 {
221 value.serialize(self)
223 }
224
225 fn serialize_newtype_variant<T>(
226 self,
227 _name: &'static str,
228 _variant_index: u32,
229 _variant: &'static str,
230 _value: &T,
231 ) -> Result<()>
232 where
233 T: ?Sized + Serialize,
234 {
235 Err(Error::Unsupported("Enum Newtype Variant"))
236 }
237
238 fn serialize_seq(self, _len: Option<usize>) -> Result<Self::SerializeSeq> {
239 self.tokens.push(NaiveToken::SeqBegin);
240 Ok(self)
241 }
242
243 fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple> {
244 self.serialize_seq(Some(len))
245 }
246
247 fn serialize_tuple_struct(
248 self,
249 _name: &'static str,
250 len: usize,
251 ) -> Result<Self::SerializeTupleStruct> {
252 self.serialize_tuple(len)
253 }
254
255 fn serialize_tuple_variant(
256 self,
257 _name: &'static str,
258 _variant_index: u32,
259 _variant: &'static str,
260 _len: usize,
261 ) -> Result<Self::SerializeTupleVariant> {
262 Ok(self)
263 }
264
265 fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap> {
266 self.tokens.push(NaiveToken::ObjBegin);
267 Ok(self)
268 }
269
270 fn serialize_struct(self, name: &'static str, len: usize) -> Result<Self::SerializeStruct> {
271 if self.tokens.is_empty() {
273 self.serialize_str(name)?;
274 }
275
276 self.serialize_map(Some(len))
277 }
278
279 fn serialize_struct_variant(
280 self,
281 _name: &'static str,
282 _variant_index: u32,
283 _variant: &'static str,
284 _len: usize,
285 ) -> Result<Self::SerializeStructVariant> {
286 Ok(self)
287 }
288}
289
290impl ser::SerializeSeq for &mut Serializer {
291 type Ok = ();
292 type Error = Error;
293
294 fn serialize_element<T>(&mut self, value: &T) -> Result<()>
295 where
296 T: ?Sized + Serialize,
297 {
298 value.serialize(&mut **self)
299 }
300
301 fn end(self) -> Result<()> {
302 self.tokens.push(NaiveToken::SeqEnd);
303 Ok(())
304 }
305}
306
307impl ser::SerializeTuple for &mut Serializer {
308 type Ok = ();
309 type Error = Error;
310
311 fn serialize_element<T>(&mut self, value: &T) -> Result<()>
312 where
313 T: ?Sized + Serialize,
314 {
315 value.serialize(&mut **self)
316 }
317
318 fn end(self) -> Result<()> {
319 self.tokens.push(NaiveToken::SeqEnd);
320 Ok(())
321 }
322}
323
324impl ser::SerializeTupleStruct for &mut Serializer {
325 type Ok = ();
326 type Error = Error;
327
328 fn serialize_field<T>(&mut self, value: &T) -> Result<()>
329 where
330 T: ?Sized + Serialize,
331 {
332 value.serialize(&mut **self)
333 }
334
335 fn end(self) -> Result<()> {
336 self.tokens.push(NaiveToken::SeqEnd);
337 Ok(())
338 }
339}
340
341impl ser::SerializeTupleVariant for &mut Serializer {
342 type Ok = ();
343 type Error = Error;
344
345 fn serialize_field<T>(&mut self, _value: &T) -> Result<()>
346 where
347 T: ?Sized + Serialize,
348 {
349 Err(Error::Unsupported("Enum Tuple Variant"))
350 }
351
352 fn end(self) -> Result<()> {
353 Err(Error::Unsupported("Enum Tuple Variant"))
354 }
355}
356
357impl ser::SerializeMap for &mut Serializer {
358 type Ok = ();
359 type Error = Error;
360
361 fn serialize_key<T>(&mut self, key: &T) -> Result<()>
362 where
363 T: ?Sized + Serialize,
364 {
365 key.serialize(&mut **self)
366 }
367
368 fn serialize_value<T>(&mut self, value: &T) -> Result<()>
369 where
370 T: ?Sized + Serialize,
371 {
372 value.serialize(&mut **self)
373 }
374
375 fn end(self) -> Result<()> {
376 self.tokens.push(NaiveToken::ObjEnd);
377 Ok(())
378 }
379}
380
381impl ser::SerializeStruct for &mut Serializer {
382 type Ok = ();
383 type Error = Error;
384
385 fn serialize_field<T>(&mut self, key: &'static str, value: &T) -> Result<()>
386 where
387 T: ?Sized + Serialize,
388 {
389 key.serialize(&mut **self)?;
390 value.serialize(&mut **self)
391 }
392
393 fn end(self) -> Result<()> {
394 self.tokens.push(NaiveToken::ObjEnd);
395 Ok(())
396 }
397}
398
399impl ser::SerializeStructVariant for &mut Serializer {
400 type Ok = ();
401 type Error = Error;
402
403 fn serialize_field<T>(&mut self, _key: &'static str, _value: &T) -> Result<()>
404 where
405 T: ?Sized + Serialize,
406 {
407 Err(Error::Unsupported("Enum Struct Variant"))
408 }
409
410 fn end(self) -> Result<()> {
411 Err(Error::Unsupported("Enum Struct Variant"))
412 }
413}