serde_keyvalue/
key_values.rs

1// Copyright 2022 The ChromiumOS Authors
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5use std::borrow::Cow;
6use std::fmt;
7use std::fmt::Debug;
8use std::fmt::Display;
9use std::num::ParseIntError;
10
11use nom::branch::alt;
12use nom::bytes::complete::escaped_transform;
13use nom::bytes::complete::is_not;
14use nom::bytes::complete::tag;
15use nom::bytes::complete::take_while;
16use nom::bytes::complete::take_while1;
17use nom::character::complete::alphanumeric1;
18use nom::character::complete::anychar;
19use nom::character::complete::char;
20use nom::character::complete::none_of;
21use nom::combinator::map;
22use nom::combinator::map_res;
23use nom::combinator::opt;
24use nom::combinator::peek;
25use nom::combinator::recognize;
26use nom::combinator::value;
27use nom::combinator::verify;
28use nom::sequence::delimited;
29use nom::sequence::pair;
30use nom::sequence::tuple;
31use nom::AsChar;
32use nom::Finish;
33use nom::IResult;
34use num_traits::Num;
35use remain::sorted;
36use serde::de;
37use serde::Deserialize;
38use serde::Deserializer;
39use thiserror::Error;
40
41#[derive(Debug, Error, PartialEq, Eq)]
42#[sorted]
43#[non_exhaustive]
44#[allow(missing_docs)]
45/// Different kinds of errors that can be returned by the parser.
46pub enum ErrorKind {
47    #[error("unexpected end of input")]
48    Eof,
49    #[error("expected a boolean")]
50    ExpectedBoolean,
51    #[error("expected ']'")]
52    ExpectedCloseBracket,
53    #[error("expected ','")]
54    ExpectedComma,
55    #[error("expected '='")]
56    ExpectedEqual,
57    #[error("expected an identifier")]
58    ExpectedIdentifier,
59    #[error("expected '['")]
60    ExpectedOpenBracket,
61    #[error("expected a string")]
62    ExpectedString,
63    #[error("\" and ' can only be used in quoted strings")]
64    InvalidCharInString,
65    #[error("invalid characters for number or number does not fit into its destination type")]
66    InvalidNumber,
67    #[error("serde error: {0}")]
68    SerdeError(String),
69    #[error("remaining characters in input")]
70    TrailingCharacters,
71}
72
73/// Error that may be thown while parsing a key-values string.
74#[derive(Debug, Error, PartialEq, Eq)]
75pub struct ParseError {
76    /// Detailed error that occurred.
77    pub kind: ErrorKind,
78    /// Index of the error in the input string.
79    pub pos: usize,
80}
81
82impl Display for ParseError {
83    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
84        match &self.kind {
85            ErrorKind::SerdeError(s) => write!(f, "{s}"),
86            _ => write!(f, "{} at position {}", self.kind, self.pos),
87        }
88    }
89}
90
91impl de::Error for ParseError {
92    fn custom<T>(msg: T) -> Self
93    where
94        T: fmt::Display,
95    {
96        Self {
97            kind: ErrorKind::SerdeError(msg.to_string()),
98            pos: 0,
99        }
100    }
101}
102
103type Result<T> = std::result::Result<T, ParseError>;
104
105/// Returns `true` if `c` is a valid separator character.
106fn is_separator(c: Option<char>) -> bool {
107    matches!(c, Some(',') | Some(']') | None)
108}
109
110/// Nom parser for valid separators.
111fn any_separator(s: &str) -> IResult<&str, Option<char>> {
112    let next_char = s.chars().next();
113
114    if is_separator(next_char) {
115        let pos = if let Some(c) = next_char {
116            c.len_utf8()
117        } else {
118            0
119        };
120        Ok((&s[pos..], next_char))
121    } else {
122        Err(nom::Err::Error(nom::error::Error::new(
123            s,
124            nom::error::ErrorKind::Char,
125        )))
126    }
127}
128
129/// Nom parser for valid strings.
130///
131/// A string can be quoted (using single or double quotes) or not. If it is not quoted, the string
132/// is assumed to continue until the next ',', '[', or ']' character. If it is escaped, it continues
133/// until the next non-escaped quote.
134///
135/// The returned value is a slice into the current input if no characters to unescape were met,
136/// or a fully owned string if we had to unescape some characters.
137fn any_string(s: &str) -> IResult<&str, Cow<str>> {
138    // Double-quoted strings may escape " and \ characters. Since escaped strings are modified,
139    // we need to return an owned `String` instead of just a slice in the input string.
140    let double_quoted = delimited(
141        char('"'),
142        alt((
143            map(
144                escaped_transform(
145                    none_of(r#"\""#),
146                    '\\',
147                    alt((value("\"", char('"')), value("\\", char('\\')))),
148                ),
149                Cow::Owned,
150            ),
151            map(tag(""), Cow::Borrowed),
152        )),
153        char('"'),
154    );
155
156    // Single-quoted strings do not escape characters.
157    let single_quoted = map(
158        delimited(char('\''), alt((is_not(r#"'"#), tag(""))), char('\'')),
159        Cow::Borrowed,
160    );
161
162    // Unquoted strings end with the next comma or bracket and may not contain a quote or bracket
163    // character or be empty.
164    let unquoted = map(
165        take_while1(|c: char| c != ',' && c != '"' && c != '\'' && c != '[' && c != ']'),
166        Cow::Borrowed,
167    );
168
169    alt((double_quoted, single_quoted, unquoted))(s)
170}
171
172/// Nom parser for valid positive of negative numbers.
173///
174/// Hexadecimal, octal, and binary values can be specified with the `0x`, `0o` and `0b` prefixes.
175fn any_number<T>(s: &str) -> IResult<&str, T>
176where
177    T: Num<FromStrRadixErr = ParseIntError>,
178{
179    // Parses the number input and returns a tuple including the number itself (with its sign) and
180    // its radix.
181    //
182    // We move this non-generic part into its own function so it doesn't get monomorphized, which
183    // would increase the binary size more than needed.
184    fn parse_number(s: &str) -> IResult<&str, (Cow<str>, u32)> {
185        // Recognizes the sign prefix.
186        let sign = char('-');
187
188        // Recognizes the radix prefix.
189        let radix = alt((
190            value(16, tag("0x")),
191            value(8, tag("0o")),
192            value(2, tag("0b")),
193        ));
194
195        // Recognizes the trailing separator but do not consume it.
196        let separator = peek(any_separator);
197
198        // Chain of parsers: sign (optional) and radix (optional), then sequence of alphanumerical
199        // characters.
200        //
201        // Then we take all 3 recognized elements and turn them into the string and radix to pass to
202        // `from_str_radix`.
203        map(
204            tuple((opt(sign), opt(radix), alphanumeric1, separator)),
205            |(sign, radix, number, _)| {
206                // If the sign was specified, we need to build a string that contains it for
207                // `from_str_radix` to parse the number accurately. Otherwise, simply borrow the
208                // remainder of the input.
209                let num_string = if let Some(sign) = sign {
210                    Cow::Owned(sign.to_string() + number)
211                } else {
212                    Cow::Borrowed(number)
213                };
214
215                (num_string, radix.unwrap_or(10))
216            },
217        )(s)
218    }
219
220    map_res(parse_number, |(num_string, radix)| {
221        T::from_str_radix(&num_string, radix)
222    })(s)
223}
224
225/// Nom parser for booleans.
226fn any_bool(s: &str) -> IResult<&str, bool> {
227    let mut boolean = alt((value(true, tag("true")), value(false, tag("false"))));
228
229    boolean(s)
230}
231
232/// Nom parser for identifiers. An identifier may contain any alphanumeric character, as well as
233/// '_' and '-' at any place excepted the first one which cannot be '-'.
234///
235/// Usually identifiers are not allowed to start with a number, but we chose to allow this
236/// here otherwise options like "mode=2d" won't parse if "2d" is an alias for an enum variant.
237fn any_identifier(s: &str) -> IResult<&str, &str> {
238    let mut ident = recognize(pair(
239        verify(anychar, |&c| c.is_alphanum() || c == '_'),
240        take_while(|c: char| c.is_alphanum() || c == '_' || c == '-'),
241    ));
242
243    ident(s)
244}
245
246/// Serde deserializer for key-values strings.
247pub struct KeyValueDeserializer<'de> {
248    /// Full input originally received for parsing.
249    original_input: &'de str,
250    /// Input currently remaining to parse.
251    input: &'de str,
252    /// If set, then `deserialize_identifier` will take and return its content the next time it is
253    /// called instead of trying to parse an identifier from the input. This is needed to allow the
254    /// name of the first field of a struct to be omitted, e.g.
255    ///
256    ///   --block "/path/to/disk.img,ro=true"
257    ///
258    /// instead of
259    ///
260    ///   --block "path=/path/to/disk.img,ro=true"
261    next_identifier: Option<&'de str>,
262    /// Whether the '=' sign has been parsed after a key. The absence of '=' is only valid for
263    /// boolean fields, in which case the field's value will be `true`.
264    has_equal: bool,
265    /// Whether the top structure has been parsed yet or not. The top structure is the only one
266    /// that does not require to be enclosed within braces.
267    top_struct_parsed: bool,
268}
269
270impl<'de> From<&'de str> for KeyValueDeserializer<'de> {
271    fn from(input: &'de str) -> Self {
272        Self {
273            original_input: input,
274            input,
275            next_identifier: None,
276            has_equal: false,
277            top_struct_parsed: false,
278        }
279    }
280}
281
282impl<'de> KeyValueDeserializer<'de> {
283    /// Return an `kind` error for the current position of the input.
284    pub fn error_here(&self, kind: ErrorKind) -> ParseError {
285        ParseError {
286            kind,
287            pos: self.original_input.len() - self.input.len(),
288        }
289    }
290
291    /// Returns the next char in the input string without consuming it, or None
292    /// if we reached the end of input.
293    pub fn peek_char(&self) -> Option<char> {
294        self.input.chars().next()
295    }
296
297    /// Skip the next char in the input string.
298    pub fn skip_char(&mut self) {
299        let _ = self.next_char();
300    }
301
302    /// Returns the next char in the input string and consume it, or returns
303    /// None if we reached the end of input.
304    pub fn next_char(&mut self) -> Option<char> {
305        let c = self.peek_char()?;
306        self.input = &self.input[c.len_utf8()..];
307        Some(c)
308    }
309
310    /// Confirm that we have a separator (i.e. ',' or ']') character or have reached the end of the
311    /// input string.
312    fn confirm_separator(&mut self) -> Result<()> {
313        // We must have a comma or end of input after a value.
314        match self.peek_char() {
315            Some(',') => {
316                let _ = self.next_char();
317                Ok(())
318            }
319            Some(']') | None => Ok(()),
320            Some(_) => Err(self.error_here(ErrorKind::ExpectedComma)),
321        }
322    }
323
324    /// Attempts to parse an identifier, either for a key or for the value of an enum type.
325    pub fn parse_identifier(&mut self) -> Result<&'de str> {
326        let (remainder, res) = any_identifier(self.input)
327            .finish()
328            .map_err(|_| self.error_here(ErrorKind::ExpectedIdentifier))?;
329
330        self.input = remainder;
331        Ok(res)
332    }
333
334    /// Attempts to parse a string.
335    pub fn parse_string(&mut self) -> Result<Cow<'de, str>> {
336        let (remainder, res) =
337            any_string(self.input)
338                .finish()
339                .map_err(|e: nom::error::Error<_>| {
340                    self.input = e.input;
341                    // Any error means we did not have a well-formed string.
342                    self.error_here(ErrorKind::ExpectedString)
343                })?;
344
345        self.input = remainder;
346
347        // The character following a string will be either a comma, a closing bracket, or EOS. If
348        // we have something else, this means an unquoted string should probably have been quoted.
349        if is_separator(self.peek_char()) {
350            Ok(res)
351        } else {
352            Err(self.error_here(ErrorKind::InvalidCharInString))
353        }
354    }
355
356    /// Attempt to parse a boolean.
357    pub fn parse_bool(&mut self) -> Result<bool> {
358        let (remainder, res) =
359            any_bool(self.input)
360                .finish()
361                .map_err(|e: nom::error::Error<_>| {
362                    self.input = e.input;
363                    self.error_here(ErrorKind::ExpectedBoolean)
364                })?;
365
366        self.input = remainder;
367        Ok(res)
368    }
369
370    /// Attempt to parse a positive or negative number.
371    pub fn parse_number<T>(&mut self) -> Result<T>
372    where
373        T: Num<FromStrRadixErr = ParseIntError>,
374    {
375        let (remainder, val) = any_number(self.input)
376            .finish()
377            .map_err(|_| self.error_here(ErrorKind::InvalidNumber))?;
378
379        self.input = remainder;
380        Ok(val)
381    }
382
383    /// Consume this deserializer and return a `TrailingCharacters` error if some input was
384    /// remaining.
385    ///
386    /// This is useful to confirm that the whole input has been consumed without any extra elements.
387    pub fn finish(self) -> Result<()> {
388        if self.input.is_empty() {
389            Ok(())
390        } else {
391            Err(self.error_here(ErrorKind::TrailingCharacters))
392        }
393    }
394}
395
396impl<'de> de::MapAccess<'de> for KeyValueDeserializer<'de> {
397    type Error = ParseError;
398
399    fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>>
400    where
401        K: de::DeserializeSeed<'de>,
402    {
403        // Detect end of input or struct.
404        match self.peek_char() {
405            None | Some(']') => return Ok(None),
406            _ => (),
407        }
408
409        self.has_equal = false;
410
411        let had_implicit_identifier = self.next_identifier.is_some();
412        let val = seed.deserialize(&mut *self).map(Some)?;
413        // We just "deserialized" the content of `next_identifier`, so there should be no equal
414        // character in the input. We can return now.
415        if had_implicit_identifier {
416            self.has_equal = true;
417            return Ok(val);
418        }
419
420        match self.peek_char() {
421            // We expect an equal after an identifier.
422            Some('=') => {
423                self.skip_char();
424                self.has_equal = true;
425                Ok(val)
426            }
427            // Ok if we are parsing a boolean where an empty value means true.
428            c if is_separator(c) => Ok(val),
429            _ => Err(self.error_here(ErrorKind::ExpectedEqual)),
430        }
431    }
432
433    fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value>
434    where
435        V: de::DeserializeSeed<'de>,
436    {
437        let val = seed.deserialize(&mut *self)?;
438
439        self.confirm_separator()?;
440
441        Ok(val)
442    }
443}
444
445/// `MapAccess` for a map with no members specified.
446///
447/// This is used to allow a struct enum type to be specified without `[` and `]`, in which case
448/// all its members will take their default value:
449///
450/// ```
451/// # use serde_keyvalue::from_key_values;
452/// # use serde::Deserialize;
453/// #[derive(Deserialize, PartialEq, Eq, Debug)]
454/// #[serde(rename_all = "kebab-case")]
455/// enum FlipMode {
456///     Active {
457///         #[serde(default)]
458///         switch1: bool,
459///         #[serde(default)]
460///         switch2: bool,
461///     },
462/// }
463/// #[derive(Deserialize, PartialEq, Eq, Debug)]
464/// struct TestStruct {
465///     mode: FlipMode,
466/// }
467/// let res: TestStruct = from_key_values("mode=active").unwrap();
468/// assert_eq!(
469///     res,
470///     TestStruct {
471///         mode: FlipMode::Active {
472///             switch1: false,
473///             switch2: false
474///         }
475///     }
476///  );
477/// ```
478struct EmptyMapAccess;
479
480impl<'de> de::MapAccess<'de> for EmptyMapAccess {
481    type Error = ParseError;
482
483    fn next_key_seed<K>(&mut self, _seed: K) -> Result<Option<K::Value>>
484    where
485        K: de::DeserializeSeed<'de>,
486    {
487        Ok(None)
488    }
489
490    fn next_value_seed<V>(&mut self, _seed: V) -> Result<V::Value>
491    where
492        V: de::DeserializeSeed<'de>,
493    {
494        // Never reached because `next_key_seed` never returns a valid key.
495        unreachable!()
496    }
497}
498
499impl<'de> de::EnumAccess<'de> for &mut KeyValueDeserializer<'de> {
500    type Error = ParseError;
501    type Variant = Self;
502
503    fn variant_seed<V>(self, seed: V) -> Result<(V::Value, Self::Variant)>
504    where
505        V: de::DeserializeSeed<'de>,
506    {
507        let val = seed.deserialize(&mut *self)?;
508        Ok((val, self))
509    }
510}
511
512impl<'de> de::VariantAccess<'de> for &mut KeyValueDeserializer<'de> {
513    type Error = ParseError;
514
515    fn unit_variant(self) -> Result<()> {
516        Ok(())
517    }
518
519    fn newtype_variant_seed<T>(self, _seed: T) -> Result<T::Value>
520    where
521        T: de::DeserializeSeed<'de>,
522    {
523        unimplemented!()
524    }
525
526    fn tuple_variant<V>(self, len: usize, visitor: V) -> Result<V::Value>
527    where
528        V: de::Visitor<'de>,
529    {
530        self.deserialize_tuple(len, visitor)
531    }
532
533    fn struct_variant<V>(self, _fields: &'static [&'static str], visitor: V) -> Result<V::Value>
534    where
535        V: de::Visitor<'de>,
536    {
537        if self.peek_char() == Some('[') {
538            self.next_char();
539            let val = self.deserialize_map(visitor)?;
540
541            if self.peek_char() != Some(']') {
542                Err(self.error_here(ErrorKind::ExpectedCloseBracket))
543            } else {
544                self.next_char();
545                Ok(val)
546            }
547        } else {
548            // The `EmptyMapAccess` failing to parse means that this enum must take arguments, i.e.
549            // that an opening bracket is expected.
550            visitor
551                .visit_map(EmptyMapAccess)
552                .map_err(|_| self.error_here(ErrorKind::ExpectedOpenBracket))
553        }
554    }
555}
556
557impl<'de> de::SeqAccess<'de> for KeyValueDeserializer<'de> {
558    type Error = ParseError;
559
560    fn next_element_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>>
561    where
562        T: de::DeserializeSeed<'de>,
563    {
564        if self.peek_char() == Some(']') {
565            return Ok(None);
566        }
567
568        let value = seed.deserialize(&mut *self)?;
569
570        self.confirm_separator()?;
571
572        Ok(Some(value))
573    }
574}
575
576impl<'de> de::Deserializer<'de> for &mut KeyValueDeserializer<'de> {
577    type Error = ParseError;
578
579    fn deserialize_any<V>(self, visitor: V) -> Result<V::Value>
580    where
581        V: serde::de::Visitor<'de>,
582    {
583        match self.peek_char() {
584            // If we have no value following, then we are dealing with a boolean flag.
585            c if is_separator(c) => return self.deserialize_bool(visitor),
586            // Opening bracket means we have a sequence.
587            Some('[') => return self.deserialize_seq(visitor),
588            _ => (),
589        }
590
591        // This is ambiguous as technically any argument could be an unquoted string. However we
592        // don't have any type information here, so try to guess it on a best-effort basis...
593        if any_number::<i64>(self.input).is_ok() {
594            self.deserialize_i64(visitor)
595        } else if any_number::<u64>(self.input).is_ok() {
596            self.deserialize_u64(visitor)
597        } else if any_bool(self.input).is_ok() {
598            self.deserialize_bool(visitor)
599        } else {
600            self.deserialize_str(visitor)
601        }
602    }
603
604    fn deserialize_bool<V>(self, visitor: V) -> Result<V::Value>
605    where
606        V: serde::de::Visitor<'de>,
607    {
608        // It is valid to just mention a bool as a flag and not specify its value - in this case
609        // the value is set as `true`.
610        let val = if self.has_equal {
611            self.parse_bool()?
612        } else {
613            true
614        };
615        visitor.visit_bool(val)
616    }
617
618    fn deserialize_i8<V>(self, visitor: V) -> Result<V::Value>
619    where
620        V: serde::de::Visitor<'de>,
621    {
622        visitor.visit_i8(self.parse_number()?)
623    }
624
625    fn deserialize_i16<V>(self, visitor: V) -> Result<V::Value>
626    where
627        V: serde::de::Visitor<'de>,
628    {
629        visitor.visit_i16(self.parse_number()?)
630    }
631
632    fn deserialize_i32<V>(self, visitor: V) -> Result<V::Value>
633    where
634        V: serde::de::Visitor<'de>,
635    {
636        visitor.visit_i32(self.parse_number()?)
637    }
638
639    fn deserialize_i64<V>(self, visitor: V) -> Result<V::Value>
640    where
641        V: serde::de::Visitor<'de>,
642    {
643        visitor.visit_i64(self.parse_number()?)
644    }
645
646    fn deserialize_u8<V>(self, visitor: V) -> Result<V::Value>
647    where
648        V: serde::de::Visitor<'de>,
649    {
650        visitor.visit_u8(self.parse_number()?)
651    }
652
653    fn deserialize_u16<V>(self, visitor: V) -> Result<V::Value>
654    where
655        V: serde::de::Visitor<'de>,
656    {
657        visitor.visit_u16(self.parse_number()?)
658    }
659
660    fn deserialize_u32<V>(self, visitor: V) -> Result<V::Value>
661    where
662        V: serde::de::Visitor<'de>,
663    {
664        visitor.visit_u32(self.parse_number()?)
665    }
666
667    fn deserialize_u64<V>(self, visitor: V) -> Result<V::Value>
668    where
669        V: serde::de::Visitor<'de>,
670    {
671        visitor.visit_u64(self.parse_number()?)
672    }
673
674    fn deserialize_f32<V>(self, _visitor: V) -> Result<V::Value>
675    where
676        V: serde::de::Visitor<'de>,
677    {
678        unimplemented!()
679    }
680
681    fn deserialize_f64<V>(self, _visitor: V) -> Result<V::Value>
682    where
683        V: serde::de::Visitor<'de>,
684    {
685        unimplemented!()
686    }
687
688    fn deserialize_char<V>(self, visitor: V) -> Result<V::Value>
689    where
690        V: serde::de::Visitor<'de>,
691    {
692        visitor.visit_char(
693            self.next_char()
694                .ok_or_else(|| self.error_here(ErrorKind::Eof))?,
695        )
696    }
697
698    fn deserialize_str<V>(self, visitor: V) -> Result<V::Value>
699    where
700        V: serde::de::Visitor<'de>,
701    {
702        match self.parse_string()? {
703            Cow::Borrowed(s) => visitor.visit_borrowed_str(s),
704            Cow::Owned(s) => visitor.visit_string(s),
705        }
706    }
707
708    fn deserialize_string<V>(self, visitor: V) -> Result<V::Value>
709    where
710        V: serde::de::Visitor<'de>,
711    {
712        self.deserialize_str(visitor)
713    }
714
715    fn deserialize_bytes<V>(self, _visitor: V) -> Result<V::Value>
716    where
717        V: serde::de::Visitor<'de>,
718    {
719        unimplemented!()
720    }
721
722    fn deserialize_byte_buf<V>(self, visitor: V) -> Result<V::Value>
723    where
724        V: serde::de::Visitor<'de>,
725    {
726        self.deserialize_bytes(visitor)
727    }
728
729    fn deserialize_option<V>(self, visitor: V) -> Result<V::Value>
730    where
731        V: serde::de::Visitor<'de>,
732    {
733        // The fact that an option is specified implies that is exists, hence we always visit
734        // Some() here.
735        visitor.visit_some(self)
736    }
737
738    fn deserialize_unit<V>(self, visitor: V) -> Result<V::Value>
739    where
740        V: serde::de::Visitor<'de>,
741    {
742        visitor.visit_unit()
743    }
744
745    fn deserialize_unit_struct<V>(self, _name: &'static str, visitor: V) -> Result<V::Value>
746    where
747        V: serde::de::Visitor<'de>,
748    {
749        self.deserialize_unit(visitor)
750    }
751
752    fn deserialize_newtype_struct<V>(self, _name: &'static str, visitor: V) -> Result<V::Value>
753    where
754        V: serde::de::Visitor<'de>,
755    {
756        visitor.visit_newtype_struct(self)
757    }
758
759    fn deserialize_seq<V>(self, visitor: V) -> Result<V::Value>
760    where
761        V: serde::de::Visitor<'de>,
762    {
763        if self.peek_char() == Some('[') {
764            self.next_char();
765            let val = visitor.visit_seq(&mut *self)?;
766
767            if self.peek_char() != Some(']') {
768                Err(self.error_here(ErrorKind::ExpectedCloseBracket))
769            } else {
770                self.next_char();
771                Ok(val)
772            }
773        } else {
774            // The `EmptyMapAccess` failing to parse means that this sequence must take arguments,
775            // i.e. that an opening bracket is expected.
776            visitor
777                .visit_map(EmptyMapAccess)
778                .map_err(|_| self.error_here(ErrorKind::ExpectedOpenBracket))
779        }
780    }
781
782    fn deserialize_tuple<V>(self, _len: usize, visitor: V) -> Result<V::Value>
783    where
784        V: serde::de::Visitor<'de>,
785    {
786        self.deserialize_seq(visitor)
787    }
788
789    fn deserialize_tuple_struct<V>(
790        self,
791        _name: &'static str,
792        _len: usize,
793        _visitor: V,
794    ) -> Result<V::Value>
795    where
796        V: serde::de::Visitor<'de>,
797    {
798        unimplemented!()
799    }
800
801    fn deserialize_map<V>(self, visitor: V) -> Result<V::Value>
802    where
803        V: serde::de::Visitor<'de>,
804    {
805        // The top structure (i.e. the first structure that we will ever parse) does not need to be
806        // enclosed in braces, but inner structures do.
807        //
808        // We need to do this here as well as in `deserialize_struct` because the top-element of
809        // flattened structs will be a map, not a struct.
810        self.top_struct_parsed = true;
811
812        visitor.visit_map(self)
813    }
814
815    fn deserialize_struct<V>(
816        self,
817        _name: &'static str,
818        fields: &'static [&'static str],
819        visitor: V,
820    ) -> Result<V::Value>
821    where
822        V: serde::de::Visitor<'de>,
823    {
824        // The top structure (i.e. the first structure that we will ever parse) does not need to be
825        // enclosed in braces, but inner structures do.
826        let top_struct_parsed = std::mem::replace(&mut self.top_struct_parsed, true);
827
828        if top_struct_parsed {
829            if self.peek_char() == Some('[') {
830                self.next_char();
831            } else {
832                // The `EmptyMapAccess` failing to parse means that this struct must take
833                // arguments, i.e. that an opening bracket is expected.
834                return visitor
835                    .visit_map(EmptyMapAccess)
836                    .map_err(|_| self.error_here(ErrorKind::ExpectedOpenBracket));
837            }
838        }
839
840        // The name of the first field of a struct can be omitted (see documentation of
841        // `next_identifier` for details).
842        //
843        // To detect this, peek the next identifier, and check if the character following is '='. If
844        // it is not, then we may have a value in first position, unless the value is identical to
845        // one of the field's name - in this case, assume this is a boolean using the flag syntax.
846        self.next_identifier = match any_identifier(self.input) {
847            Ok((_, s)) => match self.input.chars().nth(s.chars().count()) {
848                Some('=') => None,
849                _ => {
850                    if fields.contains(&s) {
851                        None
852                    } else {
853                        fields.first().copied()
854                    }
855                }
856            },
857            // Not an identifier, probably means this is a value for the first field then.
858            Err(_) => fields.first().copied(),
859        };
860
861        let ret = visitor.visit_map(&mut *self)?;
862
863        if top_struct_parsed {
864            if self.peek_char() == Some(']') {
865                self.next_char();
866            } else {
867                return Err(self.error_here(ErrorKind::ExpectedCloseBracket));
868            }
869        }
870
871        Ok(ret)
872    }
873
874    fn deserialize_enum<V>(
875        self,
876        _name: &'static str,
877        _variants: &'static [&'static str],
878        visitor: V,
879    ) -> Result<V::Value>
880    where
881        V: serde::de::Visitor<'de>,
882    {
883        visitor.visit_enum(self)
884    }
885
886    fn deserialize_identifier<V>(self, visitor: V) -> Result<V::Value>
887    where
888        V: serde::de::Visitor<'de>,
889    {
890        let identifier = self
891            .next_identifier
892            .take()
893            .map_or_else(|| self.parse_identifier(), Ok)?;
894
895        visitor.visit_borrowed_str(identifier)
896    }
897
898    fn deserialize_ignored_any<V>(self, visitor: V) -> Result<V::Value>
899    where
900        V: serde::de::Visitor<'de>,
901    {
902        self.deserialize_any(visitor)
903    }
904}
905
906/// Attempts to deserialize `T` from the key-values string `input`.
907pub fn from_key_values<'a, T>(input: &'a str) -> Result<T>
908where
909    T: Deserialize<'a>,
910{
911    let mut deserializer = KeyValueDeserializer::from(input);
912    let ret = T::deserialize(&mut deserializer)?;
913    deserializer.finish()?;
914
915    Ok(ret)
916}
917
918#[cfg(test)]
919mod tests {
920    use std::collections::BTreeSet;
921    use std::path::PathBuf;
922
923    use super::*;
924
925    #[derive(Deserialize, PartialEq, Debug)]
926    struct SingleStruct<T> {
927        m: T,
928    }
929
930    #[test]
931    fn nom_any_separator() {
932        let test_str = ",foo";
933        assert_eq!(any_separator(test_str), Ok((&test_str[1..], Some(','))));
934        let test_str = "]bar";
935        assert_eq!(any_separator(test_str), Ok((&test_str[1..], Some(']'))));
936        let test_str = "";
937        assert_eq!(any_separator(test_str), Ok((test_str, None)));
938
939        let test_str = "something,anything";
940        assert_eq!(
941            any_separator(test_str),
942            Err(nom::Err::Error(nom::error::Error::new(
943                test_str,
944                nom::error::ErrorKind::Char
945            )))
946        );
947    }
948
949    #[test]
950    fn deserialize_number() {
951        let res = from_key_values::<SingleStruct<usize>>("m=54").unwrap();
952        assert_eq!(res.m, 54);
953
954        let res = from_key_values::<SingleStruct<isize>>("m=-54").unwrap();
955        assert_eq!(res.m, -54);
956
957        // Parsing a signed into an unsigned?
958        let res = from_key_values::<SingleStruct<u32>>("m=-54").unwrap_err();
959        assert_eq!(
960            res,
961            ParseError {
962                kind: ErrorKind::InvalidNumber,
963                pos: 2
964            }
965        );
966
967        // Value too big for a signed?
968        let val = i32::MAX as u32 + 1;
969        let res = from_key_values::<SingleStruct<i32>>(&format!("m={val}")).unwrap_err();
970        assert_eq!(
971            res,
972            ParseError {
973                kind: ErrorKind::InvalidNumber,
974                pos: 2
975            }
976        );
977
978        // Not a number.
979        let res = from_key_values::<SingleStruct<usize>>("m=test").unwrap_err();
980        assert_eq!(
981            res,
982            ParseError {
983                kind: ErrorKind::InvalidNumber,
984                pos: 2,
985            }
986        );
987
988        // Parsing hex values
989        let res: SingleStruct<usize> =
990            from_key_values::<SingleStruct<usize>>("m=0x1234abcd").unwrap();
991        assert_eq!(res.m, 0x1234abcd);
992        let res: SingleStruct<isize> =
993            from_key_values::<SingleStruct<isize>>("m=-0x1234abcd").unwrap();
994        assert_eq!(res.m, -0x1234abcd);
995
996        // Hex value outside range
997        let res: ParseError = from_key_values::<SingleStruct<usize>>("m=0xg").unwrap_err();
998        assert_eq!(
999            res,
1000            ParseError {
1001                kind: ErrorKind::InvalidNumber,
1002                pos: 2,
1003            }
1004        );
1005
1006        // Parsing octal values
1007        let res: SingleStruct<usize> = from_key_values::<SingleStruct<usize>>("m=0o755").unwrap();
1008        assert_eq!(res.m, 0o755);
1009        let res: SingleStruct<isize> = from_key_values::<SingleStruct<isize>>("m=-0o755").unwrap();
1010        assert_eq!(res.m, -0o755);
1011
1012        // Octal value outside range
1013        let res: ParseError = from_key_values::<SingleStruct<usize>>("m=0o8").unwrap_err();
1014        assert_eq!(
1015            res,
1016            ParseError {
1017                kind: ErrorKind::InvalidNumber,
1018                pos: 2,
1019            }
1020        );
1021
1022        // Parsing binary values
1023        let res: SingleStruct<usize> = from_key_values::<SingleStruct<usize>>("m=0b1100").unwrap();
1024        assert_eq!(res.m, 0b1100);
1025        let res: SingleStruct<isize> = from_key_values::<SingleStruct<isize>>("m=-0b1100").unwrap();
1026        assert_eq!(res.m, -0b1100);
1027
1028        // Binary value outside range
1029        let res: ParseError = from_key_values::<SingleStruct<usize>>("m=0b2").unwrap_err();
1030        assert_eq!(
1031            res,
1032            ParseError {
1033                kind: ErrorKind::InvalidNumber,
1034                pos: 2,
1035            }
1036        );
1037    }
1038
1039    #[test]
1040    fn deserialize_string() {
1041        let kv = "m=John";
1042        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1043        assert_eq!(res.m, "John".to_string());
1044
1045        // Spaces are valid (but not recommended) in unquoted strings.
1046        let kv = "m=John Doe";
1047        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1048        assert_eq!(res.m, "John Doe".to_string());
1049
1050        // Empty string is not valid if unquoted
1051        let kv = "m=";
1052        let err = from_key_values::<SingleStruct<String>>(kv).unwrap_err();
1053        assert_eq!(
1054            err,
1055            ParseError {
1056                kind: ErrorKind::ExpectedString,
1057                pos: 2
1058            }
1059        );
1060
1061        // Quoted strings.
1062        let kv = r#"m="John Doe""#;
1063        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1064        assert_eq!(res.m, "John Doe".to_string());
1065        let kv = r#"m='John Doe'"#;
1066        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1067        assert_eq!(res.m, "John Doe".to_string());
1068
1069        // Empty quoted strings.
1070        let kv = r#"m="""#;
1071        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1072        assert_eq!(res.m, "".to_string());
1073        let kv = r#"m=''"#;
1074        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1075        assert_eq!(res.m, "".to_string());
1076
1077        // "=", ",", "[", "]" and "'" in quote.
1078        let kv = r#"m="val = [10, 20, 'a']""#;
1079        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1080        assert_eq!(res.m, r#"val = [10, 20, 'a']"#.to_string());
1081
1082        // Quotes in unquoted strings are forbidden.
1083        let kv = r#"m=val="a""#;
1084        let err = from_key_values::<SingleStruct<String>>(kv).unwrap_err();
1085        assert_eq!(
1086            err,
1087            ParseError {
1088                kind: ErrorKind::InvalidCharInString,
1089                pos: 6
1090            }
1091        );
1092        let kv = r#"m=val='a'"#;
1093        let err = from_key_values::<SingleStruct<String>>(kv).unwrap_err();
1094        assert_eq!(
1095            err,
1096            ParseError {
1097                kind: ErrorKind::InvalidCharInString,
1098                pos: 6
1099            }
1100        );
1101
1102        // Brackets in unquoted strings are forbidden.
1103        let kv = r#"m=val=[a]"#;
1104        let err = from_key_values::<SingleStruct<String>>(kv).unwrap_err();
1105        assert_eq!(
1106            err,
1107            ParseError {
1108                kind: ErrorKind::InvalidCharInString,
1109                pos: 6
1110            }
1111        );
1112
1113        // Numbers and booleans are technically valid strings.
1114        let kv = "m=10";
1115        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1116        assert_eq!(res.m, "10".to_string());
1117        let kv = "m=false";
1118        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1119        assert_eq!(res.m, "false".to_string());
1120
1121        // Escaped quote.
1122        let kv = r#"m="Escaped \" quote""#;
1123        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1124        assert_eq!(res.m, r#"Escaped " quote"#.to_string());
1125
1126        // Escaped slash at end of string.
1127        let kv = r#"m="Escaped slash\\""#;
1128        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1129        assert_eq!(res.m, r"Escaped slash\".to_string());
1130
1131        // Characters within single quotes should not be escaped.
1132        let kv = r#"m='Escaped \" quote'"#;
1133        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1134        assert_eq!(res.m, r#"Escaped \" quote"#.to_string());
1135        let kv = r"m='Escaped slash\\'";
1136        let res = from_key_values::<SingleStruct<String>>(kv).unwrap();
1137        assert_eq!(res.m, r"Escaped slash\\".to_string());
1138    }
1139
1140    #[test]
1141    fn deserialize_unit() {
1142        from_key_values::<SingleStruct<()>>("m").unwrap();
1143        from_key_values::<SingleStruct<()>>("m=").unwrap();
1144
1145        from_key_values::<SingleStruct<()>>("").unwrap_err();
1146        from_key_values::<SingleStruct<()>>("p").unwrap_err();
1147        from_key_values::<SingleStruct<()>>("m=10").unwrap_err();
1148    }
1149
1150    #[test]
1151    fn deserialize_bool() {
1152        let res = from_key_values::<SingleStruct<bool>>("m=true").unwrap();
1153        assert!(res.m);
1154
1155        let res = from_key_values::<SingleStruct<bool>>("m=false").unwrap();
1156        assert!(!res.m);
1157
1158        let res = from_key_values::<SingleStruct<bool>>("m").unwrap();
1159        assert!(res.m);
1160
1161        let res = from_key_values::<SingleStruct<bool>>("m=10").unwrap_err();
1162        assert_eq!(
1163            res,
1164            ParseError {
1165                kind: ErrorKind::ExpectedBoolean,
1166                pos: 2,
1167            }
1168        );
1169
1170        let res = from_key_values::<SingleStruct<bool>>("m=").unwrap_err();
1171        assert_eq!(
1172            res,
1173            ParseError {
1174                kind: ErrorKind::ExpectedBoolean,
1175                pos: 2,
1176            }
1177        );
1178    }
1179
1180    #[test]
1181    fn deserialize_complex_struct() {
1182        #[derive(Deserialize, PartialEq, Debug)]
1183        struct TestStruct {
1184            num: usize,
1185            path: PathBuf,
1186            enable: bool,
1187        }
1188        let kv = "num=54,path=/dev/foomatic,enable=false";
1189        let res = from_key_values::<TestStruct>(kv).unwrap();
1190        assert_eq!(
1191            res,
1192            TestStruct {
1193                num: 54,
1194                path: "/dev/foomatic".into(),
1195                enable: false,
1196            }
1197        );
1198
1199        let kv = "num=0x54,path=/dev/foomatic,enable=false";
1200        let res = from_key_values::<TestStruct>(kv).unwrap();
1201        assert_eq!(
1202            res,
1203            TestStruct {
1204                num: 0x54,
1205                path: "/dev/foomatic".into(),
1206                enable: false,
1207            }
1208        );
1209
1210        let kv = "enable,path=/usr/lib/libossom.so.1,num=12";
1211        let res = from_key_values::<TestStruct>(kv).unwrap();
1212        assert_eq!(
1213            res,
1214            TestStruct {
1215                num: 12,
1216                path: "/usr/lib/libossom.so.1".into(),
1217                enable: true,
1218            }
1219        );
1220
1221        // Braces specified at top-level.
1222        let kv = "[enable,path=/usr/lib/libossom.so.1,num=12]";
1223        assert!(from_key_values::<TestStruct>(kv).is_err());
1224    }
1225
1226    #[test]
1227    fn deserialize_unknown_field() {
1228        #[derive(Deserialize, PartialEq, Debug)]
1229        #[serde(deny_unknown_fields)]
1230        struct TestStruct {
1231            num: usize,
1232            path: PathBuf,
1233            enable: bool,
1234        }
1235
1236        let kv = "enable,path=/usr/lib/libossom.so.1,num=12,foo=bar";
1237        assert!(from_key_values::<TestStruct>(kv).is_err());
1238    }
1239
1240    #[test]
1241    fn deserialize_option() {
1242        #[derive(Deserialize, PartialEq, Debug)]
1243        struct TestStruct {
1244            num: u32,
1245            opt: Option<u32>,
1246        }
1247        let kv = "num=16,opt=12";
1248        let res: TestStruct = from_key_values(kv).unwrap();
1249        assert_eq!(
1250            res,
1251            TestStruct {
1252                num: 16,
1253                opt: Some(12),
1254            }
1255        );
1256
1257        let kv = "num=16";
1258        let res: TestStruct = from_key_values(kv).unwrap();
1259        assert_eq!(res, TestStruct { num: 16, opt: None });
1260
1261        let kv = "";
1262        assert!(from_key_values::<TestStruct>(kv).is_err());
1263    }
1264
1265    #[test]
1266    fn deserialize_optional_struct_with_default() {
1267        #[derive(Deserialize, PartialEq, Debug)]
1268        struct DefaultStruct {
1269            #[serde(default)]
1270            param: u32,
1271        }
1272
1273        #[derive(Deserialize, PartialEq, Debug)]
1274        struct TestStruct {
1275            flag: Option<DefaultStruct>,
1276        }
1277
1278        // Specify member explicitly
1279        let kv = "flag=[param=12]";
1280        let res: TestStruct = from_key_values(kv).unwrap();
1281        assert_eq!(
1282            res,
1283            TestStruct {
1284                flag: Some(DefaultStruct { param: 12 })
1285            }
1286        );
1287
1288        // No member specified, braces present.
1289        let kv = "flag=[]";
1290        let res: TestStruct = from_key_values(kv).unwrap();
1291        assert_eq!(
1292            res,
1293            TestStruct {
1294                flag: Some(DefaultStruct { param: 0 })
1295            }
1296        );
1297
1298        // No member specified, no braces.
1299        let kv = "flag=";
1300        let res: TestStruct = from_key_values(kv).unwrap();
1301        assert_eq!(
1302            res,
1303            TestStruct {
1304                flag: Some(DefaultStruct { param: 0 })
1305            }
1306        );
1307
1308        // No member specified, no braces, no equal sign.
1309        let kv = "flag";
1310        let res: TestStruct = from_key_values(kv).unwrap();
1311        assert_eq!(
1312            res,
1313            TestStruct {
1314                flag: Some(DefaultStruct { param: 0 })
1315            }
1316        );
1317
1318        // No closing brace.
1319        let kv = "flag=[";
1320        assert!(from_key_values::<TestStruct>(kv).is_err());
1321
1322        // No opening brace.
1323        let kv = "flag=]";
1324        assert!(from_key_values::<TestStruct>(kv).is_err());
1325    }
1326
1327    #[test]
1328    fn deserialize_optional_struct_within_flattened() {
1329        #[derive(Deserialize, PartialEq, Debug)]
1330        struct FlatStruct {
1331            a: u32,
1332            #[serde(default)]
1333            b: String,
1334        }
1335
1336        #[derive(Deserialize, PartialEq, Debug)]
1337        struct DefaultStruct {
1338            #[serde(default)]
1339            param: u32,
1340        }
1341
1342        #[derive(Deserialize, PartialEq, Debug)]
1343        struct TestStruct {
1344            #[serde(flatten)]
1345            flat: FlatStruct,
1346            flag: Option<DefaultStruct>,
1347        }
1348
1349        // Everything specified.
1350        let kv = "a=10,b=foomatic,flag=[param=24]";
1351        let res: TestStruct = from_key_values(kv).unwrap();
1352        assert_eq!(
1353            res,
1354            TestStruct {
1355                flat: FlatStruct {
1356                    a: 10,
1357                    b: "foomatic".into(),
1358                },
1359                flag: Some(DefaultStruct { param: 24 })
1360            }
1361        );
1362
1363        // Flag left to default value.
1364        let kv = "a=10,b=foomatic,flag";
1365        let res: TestStruct = from_key_values(kv).unwrap();
1366        assert_eq!(
1367            res,
1368            TestStruct {
1369                flat: FlatStruct {
1370                    a: 10,
1371                    b: "foomatic".into(),
1372                },
1373                flag: Some(DefaultStruct { param: 0 })
1374            }
1375        );
1376
1377        // Flattened default value unspecified.
1378        let kv = "a=10,flag=[param=24]";
1379        let res: TestStruct = from_key_values(kv).unwrap();
1380        assert_eq!(
1381            res,
1382            TestStruct {
1383                flat: FlatStruct {
1384                    a: 10,
1385                    b: Default::default(),
1386                },
1387                flag: Some(DefaultStruct { param: 24 })
1388            }
1389        );
1390
1391        // No optional, no default value.
1392        let kv = "a=10";
1393        let res: TestStruct = from_key_values(kv).unwrap();
1394        assert_eq!(
1395            res,
1396            TestStruct {
1397                flat: FlatStruct {
1398                    a: 10,
1399                    b: Default::default(),
1400                },
1401                flag: None,
1402            }
1403        );
1404
1405        // Required member unspecified.
1406        let kv = "b=foomatic,flag=[param=24]";
1407        assert!(from_key_values::<TestStruct>(kv).is_err());
1408
1409        // Braces specified at top-level.
1410        let kv = "[a=10,b=foomatic,flag=[param=24]]";
1411        assert!(from_key_values::<TestStruct>(kv).is_err());
1412    }
1413
1414    #[test]
1415    fn deserialize_enum() {
1416        #[derive(Deserialize, PartialEq, Debug)]
1417        enum TestEnum {
1418            #[serde(rename = "first")]
1419            FirstVariant,
1420            #[serde(rename = "second")]
1421            SecondVariant,
1422        }
1423        let res: TestEnum = from_key_values("first").unwrap();
1424        assert_eq!(res, TestEnum::FirstVariant,);
1425
1426        let res: TestEnum = from_key_values("second").unwrap();
1427        assert_eq!(res, TestEnum::SecondVariant,);
1428
1429        from_key_values::<TestEnum>("third").unwrap_err();
1430    }
1431
1432    #[test]
1433    fn deserialize_embedded_enum() {
1434        #[derive(Deserialize, PartialEq, Debug)]
1435        enum TestEnum {
1436            #[serde(rename = "first")]
1437            FirstVariant,
1438            #[serde(rename = "second")]
1439            SecondVariant,
1440        }
1441        #[derive(Deserialize, PartialEq, Debug)]
1442        struct TestStruct {
1443            variant: TestEnum,
1444            #[serde(default)]
1445            active: bool,
1446        }
1447        let res: TestStruct = from_key_values("variant=first").unwrap();
1448        assert_eq!(
1449            res,
1450            TestStruct {
1451                variant: TestEnum::FirstVariant,
1452                active: false,
1453            }
1454        );
1455        let res: TestStruct = from_key_values("variant=second,active=true").unwrap();
1456        assert_eq!(
1457            res,
1458            TestStruct {
1459                variant: TestEnum::SecondVariant,
1460                active: true,
1461            }
1462        );
1463        let res: TestStruct = from_key_values("active=true,variant=second").unwrap();
1464        assert_eq!(
1465            res,
1466            TestStruct {
1467                variant: TestEnum::SecondVariant,
1468                active: true,
1469            }
1470        );
1471        let res: TestStruct = from_key_values("active,variant=second").unwrap();
1472        assert_eq!(
1473            res,
1474            TestStruct {
1475                variant: TestEnum::SecondVariant,
1476                active: true,
1477            }
1478        );
1479        let res: TestStruct = from_key_values("active=false,variant=second").unwrap();
1480        assert_eq!(
1481            res,
1482            TestStruct {
1483                variant: TestEnum::SecondVariant,
1484                active: false,
1485            }
1486        );
1487    }
1488
1489    #[test]
1490    fn deserialize_untagged_enum() {
1491        #[derive(Deserialize, PartialEq, Debug)]
1492        #[serde(untagged)]
1493        enum TestEnum {
1494            FirstVariant { first: u32 },
1495            SecondVariant { second: bool },
1496        }
1497
1498        #[derive(Deserialize, PartialEq, Debug)]
1499        struct TestStruct {
1500            #[serde(flatten)]
1501            variant: TestEnum,
1502        }
1503
1504        let res: TestStruct = from_key_values("first=10").unwrap();
1505        assert_eq!(res.variant, TestEnum::FirstVariant { first: 10 });
1506
1507        let res: TestStruct = from_key_values("second=false").unwrap();
1508        assert_eq!(res.variant, TestEnum::SecondVariant { second: false },);
1509
1510        let res: TestStruct = from_key_values("second").unwrap();
1511        assert_eq!(res.variant, TestEnum::SecondVariant { second: true },);
1512
1513        from_key_values::<TestStruct>("third=10").unwrap_err();
1514        from_key_values::<TestStruct>("first=some_string").unwrap_err();
1515        from_key_values::<TestStruct>("second=10").unwrap_err();
1516    }
1517
1518    #[test]
1519    fn deserialize_first_arg_string() {
1520        #[derive(Deserialize, PartialEq, Debug)]
1521        struct TestStruct {
1522            name: String,
1523            num: u8,
1524        }
1525        let res: TestStruct = from_key_values("name=foo,num=12").unwrap();
1526        assert_eq!(
1527            res,
1528            TestStruct {
1529                name: "foo".into(),
1530                num: 12,
1531            }
1532        );
1533
1534        let res: TestStruct = from_key_values("foo,num=12").unwrap();
1535        assert_eq!(
1536            res,
1537            TestStruct {
1538                name: "foo".into(),
1539                num: 12,
1540            }
1541        );
1542    }
1543
1544    #[test]
1545    fn deserialize_first_arg_int() {
1546        #[derive(Deserialize, PartialEq, Debug)]
1547        struct TestStruct {
1548            num: u8,
1549            name: String,
1550        }
1551        let res: TestStruct = from_key_values("name=foo,num=12").unwrap();
1552        assert_eq!(
1553            res,
1554            TestStruct {
1555                num: 12,
1556                name: "foo".into(),
1557            }
1558        );
1559
1560        let res: TestStruct = from_key_values("12,name=foo").unwrap();
1561        assert_eq!(
1562            res,
1563            TestStruct {
1564                num: 12,
1565                name: "foo".into(),
1566            }
1567        );
1568    }
1569
1570    #[test]
1571    fn deserialize_tuple() {
1572        #[derive(Deserialize, PartialEq, Debug)]
1573        struct TestStruct {
1574            size: (u32, u32),
1575        }
1576
1577        let res: TestStruct = from_key_values("size=[320,200]").unwrap();
1578        assert_eq!(res, TestStruct { size: (320, 200) });
1579
1580        // Unterminated tuple.
1581        let err = from_key_values::<TestStruct>("size=[320]").unwrap_err();
1582        assert_eq!(
1583            err,
1584            ParseError {
1585                kind: ErrorKind::SerdeError("invalid length 1, expected a tuple of size 2".into()),
1586                pos: 0,
1587            }
1588        );
1589
1590        // Too many elements in tuple.
1591        let err = from_key_values::<TestStruct>("size=[320,200,255]").unwrap_err();
1592        assert_eq!(
1593            err,
1594            ParseError {
1595                kind: ErrorKind::ExpectedCloseBracket,
1596                pos: 14,
1597            }
1598        );
1599
1600        // Non-closed sequence is invalid.
1601        let err = from_key_values::<TestStruct>("size=[320,200").unwrap_err();
1602        assert_eq!(
1603            err,
1604            ParseError {
1605                kind: ErrorKind::ExpectedCloseBracket,
1606                pos: 13,
1607            }
1608        );
1609    }
1610
1611    #[test]
1612    fn deserialize_vector() {
1613        #[derive(Deserialize, PartialEq, Debug)]
1614        struct TestStruct {
1615            numbers: Vec<u32>,
1616        }
1617
1618        let res: TestStruct = from_key_values("numbers=[1,2,4,8,16,32,64]").unwrap();
1619        assert_eq!(
1620            res,
1621            TestStruct {
1622                numbers: vec![1, 2, 4, 8, 16, 32, 64],
1623            }
1624        );
1625    }
1626
1627    #[test]
1628    fn deserialize_vector_of_strings() {
1629        #[derive(Deserialize, PartialEq, Debug)]
1630        struct TestStruct {
1631            strs: Vec<String>,
1632        }
1633
1634        // Unquoted strings
1635        let res: TestStruct =
1636            from_key_values(r#"strs=[singleword,camel_cased,kebab-cased]"#).unwrap();
1637        assert_eq!(
1638            res,
1639            TestStruct {
1640                strs: vec![
1641                    "singleword".into(),
1642                    "camel_cased".into(),
1643                    "kebab-cased".into()
1644                ],
1645            }
1646        );
1647
1648        // All quoted strings
1649        let res: TestStruct =
1650            from_key_values(r#"strs=["first string","second string","third string"]"#).unwrap();
1651        assert_eq!(
1652            res,
1653            TestStruct {
1654                strs: vec![
1655                    "first string".into(),
1656                    "second string".into(),
1657                    "third string".into()
1658                ],
1659            }
1660        );
1661
1662        // Mix
1663        let res: TestStruct =
1664            from_key_values(r#"strs=[unquoted,"quoted string",'quoted with escape "']"#).unwrap();
1665        assert_eq!(
1666            res,
1667            TestStruct {
1668                strs: vec![
1669                    "unquoted".into(),
1670                    "quoted string".into(),
1671                    "quoted with escape \"".into()
1672                ],
1673            }
1674        );
1675    }
1676
1677    #[test]
1678    fn deserialize_vector_of_structs() {
1679        #[derive(Deserialize, PartialEq, Debug)]
1680        #[serde(deny_unknown_fields)]
1681        struct Display {
1682            size: (u32, u32),
1683            #[serde(default)]
1684            disabled: bool,
1685        }
1686
1687        #[derive(Deserialize, PartialEq, Debug)]
1688        #[serde(deny_unknown_fields)]
1689        struct TestStruct {
1690            displays: Vec<Display>,
1691            hostname: Option<String>,
1692        }
1693
1694        let res: TestStruct = from_key_values("displays=[[size=[640,480]]]").unwrap();
1695        assert_eq!(
1696            res,
1697            TestStruct {
1698                displays: vec![Display {
1699                    size: (640, 480),
1700                    disabled: false,
1701                }],
1702                hostname: None,
1703            }
1704        );
1705
1706        let res: TestStruct =
1707            from_key_values("hostname=crosmatic,displays=[[size=[800,600],disabled]]").unwrap();
1708        assert_eq!(
1709            res,
1710            TestStruct {
1711                displays: vec![Display {
1712                    size: (800, 600),
1713                    disabled: true,
1714                }],
1715                hostname: Some("crosmatic".to_string()),
1716            }
1717        );
1718
1719        // First field of a struct does not need to be named even if it is not the top-level struct.
1720        let res: TestStruct =
1721            from_key_values("displays=[[[640,480]],[[800,600],disabled]]").unwrap();
1722        assert_eq!(
1723            res,
1724            TestStruct {
1725                displays: vec![
1726                    Display {
1727                        size: (640, 480),
1728                        disabled: false,
1729                    },
1730                    Display {
1731                        size: (800, 600),
1732                        disabled: true,
1733                    }
1734                ],
1735                hostname: None,
1736            }
1737        );
1738
1739        let res: TestStruct =
1740            from_key_values("displays=[[[1024,768]],[size=[800,600],disabled]],hostname=crosmatic")
1741                .unwrap();
1742        assert_eq!(
1743            res,
1744            TestStruct {
1745                displays: vec![
1746                    Display {
1747                        size: (1024, 768),
1748                        disabled: false,
1749                    },
1750                    Display {
1751                        size: (800, 600),
1752                        disabled: true,
1753                    }
1754                ],
1755                hostname: Some("crosmatic".to_string()),
1756            }
1757        );
1758    }
1759
1760    #[test]
1761    fn deserialize_set() {
1762        #[derive(Deserialize, PartialEq, Eq, Debug, PartialOrd, Ord)]
1763        #[serde(rename_all = "kebab-case")]
1764        enum Flags {
1765            Awesome,
1766            Fluffy,
1767            Transparent,
1768        }
1769        #[derive(Deserialize, PartialEq, Debug)]
1770        struct TestStruct {
1771            flags: BTreeSet<Flags>,
1772        }
1773
1774        let res: TestStruct = from_key_values("flags=[awesome,fluffy]").unwrap();
1775        assert_eq!(
1776            res,
1777            TestStruct {
1778                flags: BTreeSet::from([Flags::Awesome, Flags::Fluffy]),
1779            }
1780        );
1781
1782        // Unknown enum variant?
1783        let err = from_key_values::<TestStruct>("flags=[awesome,spiky]").unwrap_err();
1784        assert_eq!(
1785            err,
1786            ParseError {
1787                kind: ErrorKind::SerdeError(
1788                    "unknown variant `spiky`, expected one of `awesome`, `fluffy`, `transparent`"
1789                        .into()
1790                ),
1791                pos: 0,
1792            }
1793        );
1794    }
1795
1796    #[test]
1797    fn deserialize_struct_and_tuple_enum() {
1798        #[derive(Deserialize, PartialEq, Debug)]
1799        #[serde(rename_all = "kebab-case")]
1800        enum VideoMode {
1801            Fullscreen,
1802            WindowAsTuple(u32, u32),
1803            WindowAsStruct { width: u32, height: u32 },
1804        }
1805
1806        #[derive(Deserialize, PartialEq, Debug)]
1807        struct TestStruct {
1808            mode: VideoMode,
1809        }
1810
1811        let res: TestStruct = from_key_values("mode=fullscreen").unwrap();
1812        assert_eq!(
1813            res,
1814            TestStruct {
1815                mode: VideoMode::Fullscreen
1816            }
1817        );
1818
1819        let res: TestStruct = from_key_values("mode=window-as-tuple[640,480]").unwrap();
1820        assert_eq!(
1821            res,
1822            TestStruct {
1823                mode: VideoMode::WindowAsTuple(640, 480),
1824            }
1825        );
1826
1827        // Missing values
1828        let err = from_key_values::<TestStruct>("mode=window-as-tuple").unwrap_err();
1829        assert_eq!(
1830            err,
1831            ParseError {
1832                kind: ErrorKind::ExpectedOpenBracket,
1833                pos: 20,
1834            }
1835        );
1836
1837        let res: TestStruct =
1838            from_key_values("mode=window-as-struct[width=800,height=600]").unwrap();
1839        assert_eq!(
1840            res,
1841            TestStruct {
1842                mode: VideoMode::WindowAsStruct {
1843                    width: 800,
1844                    height: 600,
1845                }
1846            }
1847        );
1848
1849        // Missing values.
1850        let err = from_key_values::<TestStruct>("mode=window-as-struct").unwrap_err();
1851        assert_eq!(
1852            err,
1853            ParseError {
1854                kind: ErrorKind::ExpectedOpenBracket,
1855                pos: 21,
1856            }
1857        );
1858    }
1859
1860    #[test]
1861    fn deserialize_struct_enum_with_default() {
1862        #[derive(Deserialize, PartialEq, Debug)]
1863        #[serde(rename_all = "kebab-case")]
1864        enum FlipMode {
1865            Inactive,
1866            Active {
1867                #[serde(default)]
1868                switch1: bool,
1869                #[serde(default)]
1870                switch2: bool,
1871            },
1872        }
1873
1874        #[derive(Deserialize, PartialEq, Debug)]
1875        struct TestStruct {
1876            mode: FlipMode,
1877        }
1878
1879        // Only specify one member and expect the other to be default.
1880        let res: TestStruct = from_key_values("mode=active[switch1=true]").unwrap();
1881        assert_eq!(
1882            res,
1883            TestStruct {
1884                mode: FlipMode::Active {
1885                    switch1: true,
1886                    switch2: false
1887                }
1888            }
1889        );
1890
1891        // Specify boolean members without explicit value.
1892        let res: TestStruct = from_key_values("mode=active[switch1,switch2]").unwrap();
1893        assert_eq!(
1894            res,
1895            TestStruct {
1896                mode: FlipMode::Active {
1897                    switch1: true,
1898                    switch2: true
1899                }
1900            }
1901        );
1902
1903        // No member specified, braces present.
1904        let res: TestStruct = from_key_values("mode=active[]").unwrap();
1905        assert_eq!(
1906            res,
1907            TestStruct {
1908                mode: FlipMode::Active {
1909                    switch1: false,
1910                    switch2: false
1911                }
1912            }
1913        );
1914
1915        // No member specified and no braces.
1916        let res: TestStruct = from_key_values("mode=active").unwrap();
1917        assert_eq!(
1918            res,
1919            TestStruct {
1920                mode: FlipMode::Active {
1921                    switch1: false,
1922                    switch2: false
1923                }
1924            }
1925        );
1926
1927        // Non-struct variant should be recognized without braces.
1928        let res: TestStruct = from_key_values("mode=inactive").unwrap();
1929        assert_eq!(
1930            res,
1931            TestStruct {
1932                mode: FlipMode::Inactive,
1933            }
1934        );
1935
1936        // Non-struct variant should not accept braces.
1937        let err = from_key_values::<TestStruct>("mode=inactive[]").unwrap_err();
1938        assert_eq!(
1939            err,
1940            ParseError {
1941                kind: ErrorKind::ExpectedComma,
1942                pos: 13,
1943            }
1944        );
1945    }
1946}