diff options
author | Sam Scott <sam.scott89@gmail.com> | 2017-05-20 22:57:58 +0100 |
---|---|---|
committer | Sam Scott <sam.scott89@gmail.com> | 2017-05-20 22:57:58 +0100 |
commit | 661cc9697a1c31abe786e45e43072800b6641871 (patch) | |
tree | 9d7d20656320d4bf5fb437d8f8d13b0e41131571 /src/de | |
parent | 6e71ba43eb6bd62f2b567224e387333016bd3a5c (diff) |
Organisational changes.
Diffstat (limited to 'src/de')
-rw-r--r-- | src/de/mod.rs | 652 | ||||
-rw-r--r-- | src/de/parse.rs | 359 |
2 files changed, 1011 insertions, 0 deletions
diff --git a/src/de/mod.rs b/src/de/mod.rs new file mode 100644 index 0000000..267b4cb --- /dev/null +++ b/src/de/mod.rs @@ -0,0 +1,652 @@ +//! Deserialization support for querystrings. + +mod parse; + +pub use de::parse::Config; + +use data_encoding; +use data_encoding::base64; + +use serde::de; +use serde::de::IntoDeserializer; +use serde::de::value::MapDeserializer; + +use url::percent_encoding; + +use std::collections::btree_map::{BTreeMap, Entry, IntoIter}; +use std::io::{self,Read}; +use std::fmt::Display; +use std::string; + +error_chain! { + errors { Custom(msg: String) } + foreign_links { + Decoding(data_encoding::decode::Error); + Io(io::Error); + Utf8(string::FromUtf8Error); + } +} + +impl Error { + fn top_level(object: &'static str) -> Self { + ErrorKind::Custom(format!("cannot deserialize {} at the top level.\ + Try deserializing into a struct.", object)).into() + + } +} + +impl de::Error for Error { + fn custom<T>(msg: T) -> Self + where T: Display { + ErrorKind::Custom(msg.to_string()).into() + } +} + +/// Deserializes a querystring from a `&[u8]`. +/// +/// ``` +/// # #[macro_use] +/// # extern crate serde_derive; +/// # extern crate serde_qs; +/// #[derive(Debug, Deserialize, PartialEq, Serialize)] +/// struct Query { +/// name: String, +/// age: u8, +/// occupation: String, +/// } +/// +/// # fn main(){ +/// let q = Query { +/// name: "Alice".to_owned(), +/// age: 24, +/// occupation: "Student".to_owned(), +/// }; +/// +/// assert_eq!( +/// serde_qs::from_bytes::<Query>( +/// "name=Alice&age=24&occupation=Student".as_bytes() +/// ).unwrap(), q); +/// # } +/// ``` +pub fn from_bytes<'de, T: de::Deserialize<'de>>(input: &[u8]) -> Result<T> { + Config::default().deserialize_bytes(input) +} + +/// Deserializes a querystring from a `&str`. +/// +/// ``` +/// # #[macro_use] +/// # extern crate serde_derive; +/// # extern crate serde_qs; +/// #[derive(Debug, Deserialize, PartialEq, Serialize)] +/// struct Query { +/// name: String, +/// age: u8, +/// occupation: String, +/// } +/// +/// # fn main(){ +/// let q = Query { +/// name: "Alice".to_owned(), +/// age: 24, +/// occupation: "Student".to_owned(), +/// }; +/// +/// assert_eq!( +/// serde_qs::from_str::<Query>("name=Alice&age=24&occupation=Student").unwrap(), +/// q); +/// # } +/// ``` +pub fn from_str<'de, T: de::Deserialize<'de>>(input: &str) -> Result<T> { + from_bytes(input.as_bytes()) +} + +/// Convenience function that reads all bytes from `reader` and deserializes +/// them with `from_bytes`. +pub fn from_reader<'de, T, R>(mut reader: R) -> Result<T> + where T: de::Deserialize<'de>, + R: Read, +{ + let mut buf = vec![]; + reader.read_to_end(&mut buf) + .map_err(|e| { + ErrorKind::Io(e) + })?; + from_bytes(&buf) +} + +/// A deserializer for the querystring format. +/// +/// Supported top-level outputs are structs and maps. +pub struct Deserializer { + iter: IntoIter<String, Level>, + value: Option<Level>, +} + +#[derive(Debug)] +pub enum Level { + Nested(BTreeMap<String, Level>), + Sequence(Vec<Level>), + Flat(String), + Invalid(&'static str), +} + +impl Deserializer { + fn with_map(map: BTreeMap<String, Level>) -> Self { + Deserializer { + iter: map.into_iter(), + value: None, + } + } + + /// Returns a new `Deserializer`. + fn with_config(config: &Config, input: &[u8]) -> Self { + let decoded = percent_encoding::percent_decode(input); + parse::Parser::new(decoded, vec![], None, config.max_depth()).to_deserializer() + + } +} + +impl<'de> de::Deserializer<'de> for Deserializer { + type Error = Error; + + fn deserialize_any<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + self.deserialize_map(visitor) + } + + fn deserialize_map<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + visitor.visit_map(self) + } + + fn deserialize_struct<V>(self, + _name: &'static str, + _fields: &'static [&'static str], + visitor: V) + -> Result<V::Value> + where V: de::Visitor<'de>, + { + self.deserialize_map(visitor) + } + + /// Throws an error. + /// + /// Sequences are not supported at the top level. + fn deserialize_seq<V>(self, _visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + Err(Error::top_level("sequence")) + } + + fn deserialize_newtype_struct<V>( + self, + _name: &'static str, + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + self.deserialize_map(visitor) + } + + /// Throws an error. + /// + /// Tuples are not supported at the top level. + fn deserialize_tuple<V>( + self, + _len: usize, + _visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + Err(Error::top_level("tuple")) + + } + + /// Throws an error. + /// + /// TupleStructs are not supported at the top level. + fn deserialize_tuple_struct<V>( + self, + _name: &'static str, + _len: usize, + _visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + Err(Error::top_level("tuple struct")) + } + + fn deserialize_enum<V>( + self, + _name: &'static str, + _variants: &'static [&'static str], + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + visitor.visit_enum(self) + } + + forward_to_deserialize_any! { + bool + u8 + u16 + u32 + u64 + i8 + i16 + i32 + i64 + f32 + f64 + char + str + string + unit + option + bytes + byte_buf + unit_struct + // seq + // seq_fixed_size + // newtype_struct + // tuple_struct + // struct + identifier + // struct_field + // tuple + // enum + ignored_any + } +} + +// use serde::de::IntoDeserializer; +// use serde::de::value::SeqDeserializer; + +impl<'de> de::MapAccess<'de> for Deserializer { + type Error = Error; + + + fn next_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>> + where K: de::DeserializeSeed<'de>, + { + if let Some((key, value)) = self.iter.next() { + self.value = Some(value); + return seed.deserialize(ParsableStringDeserializer(key)).map(Some); + }; + Ok(None) + } + + fn next_value_seed<V>(&mut self, seed: V) -> Result<V::Value> + where V: de::DeserializeSeed<'de>, + { + if let Some(v) = self.value.take() { + seed.deserialize(LevelDeserializer(v)) + } else { + Err(de::Error::custom("Somehow the list was empty after a \ + non-empty key was returned")) + } + } +} + +impl<'de> de::EnumAccess<'de> for Deserializer { + type Error = Error; + type Variant = LevelDeserializer; + + fn variant_seed<V>(mut self, seed: V) -> Result<(V::Value, Self::Variant)> + where V: de::DeserializeSeed<'de> + { + if let Some((key, value)) = self.iter.next() { + Ok((seed.deserialize(ParsableStringDeserializer(key))?, LevelDeserializer(value))) + } else { + Err(de::Error::custom("No more values")) + } + } +} + +impl<'de> de::EnumAccess<'de> for LevelDeserializer { + type Error = Error; + type Variant = Self; + + fn variant_seed<V>(self, seed: V) -> Result<(V::Value, Self::Variant)> + where V: de::DeserializeSeed<'de> + { + match self.0 { + Level::Flat(x) => { + Ok((seed.deserialize(ParsableStringDeserializer(x))?, LevelDeserializer(Level::Invalid("")))) + }, + _ => { + Err(de::Error::custom("should not be here...")) + } + } + } +} + +impl<'de> de::VariantAccess<'de> for LevelDeserializer { + type Error = Error; + fn unit_variant(self) -> Result<()> { + Ok(()) + } + + fn newtype_variant_seed<T>(self, seed: T) -> Result<T::Value> + where + T: de::DeserializeSeed<'de> + { + seed.deserialize(self) + + } + fn tuple_variant<V>( + self, + _len: usize, + visitor: V + ) -> Result<V::Value> + where + V: de::Visitor<'de> + { + de::Deserializer::deserialize_seq(self, visitor) + + } + fn struct_variant<V>( + self, + _fields: &'static [&'static str], + visitor: V + ) -> Result<V::Value> + where + V: de::Visitor<'de> + { + de::Deserializer::deserialize_map(self, visitor) + } +} + +struct LevelSeq<I: Iterator<Item=Level>>(I); + +impl<'de, I: Iterator<Item=Level>> de::SeqAccess<'de> for LevelSeq<I> { + type Error = Error; + fn next_element_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>> + where T: de::DeserializeSeed<'de> + { + if let Some(v) = self.0.next() { + seed.deserialize(LevelDeserializer(v)).map(Some) + } else { + Ok(None) + } + } +} + + + +pub struct LevelDeserializer(Level); + +macro_rules! deserialize_primitive { + ($ty:ident, $method:ident, $visit_method:ident) => ( + fn $method<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + match self.0 { + Level::Nested(_) => { + Err(de::Error::custom(format!("Expected: {:?}, got a Map", + stringify!($ty)))) + }, + Level::Sequence(_) => { + Err(de::Error::custom(format!("Expected: {:?}, got a Sequence", + stringify!($ty)))) + }, + Level::Flat(x) => { + ParsableStringDeserializer(x).$method(visitor) + }, + Level::Invalid(e) => { + Err(de::Error::custom(e)) + } + } + } + ) +} + +impl LevelDeserializer { + fn to_deserializer(self) -> Result<Deserializer> { + match self.0 { + Level::Nested(map) => { + Ok(Deserializer::with_map(map)) + }, + Level::Invalid(e) => { + Err(de::Error::custom(e)) + } + l => { + Err(de::Error::custom(format!("could not convert {:?} to Deserializer", l))) + }, + } + } +} + +impl<'de> de::Deserializer<'de> for LevelDeserializer { + type Error = Error; + + fn deserialize_any<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + match self.0 { + Level::Nested(_) => { + // Deserializer::with_map(map).deserialize_map(visitor) + self.deserialize_map(visitor) + }, + Level::Sequence(_) => { + self.deserialize_seq(visitor) + + }, + Level::Flat(x) => { + visitor.visit_string(x) + }, + Level::Invalid(e) => { + Err(de::Error::custom(e)) + } + } + } + + fn deserialize_seq<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + match self.0 { + Level::Nested(map) => { + visitor.visit_seq(LevelSeq(map.into_iter().map(|(_k, v)| v))) + }, + Level::Sequence(x) => { + visitor.visit_seq(LevelSeq(x.into_iter())) + }, + Level::Invalid(e) => { + Err(de::Error::custom(e)) + }, + x => { + visitor.visit_seq(LevelSeq(vec![x].into_iter())) + }, + } + } + + fn deserialize_option<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + match self.0 { + Level::Flat(ref x) if x == "" => { + visitor.visit_none() + }, + _ => { + visitor.visit_some(self) + }, + } + } + + fn deserialize_enum<V>( + self, + name: &'static str, + variants: &'static [&'static str], + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + match self.0 { + Level::Nested(map) => { + Deserializer::with_map(map).deserialize_enum(name, variants, visitor) + }, + Level::Flat(_) => { + visitor.visit_enum(self) + }, + _ => { + Err(de::Error::custom("value does not appear to be a sequence")) + }, + } + } + + fn deserialize_map<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + self.to_deserializer()?.deserialize_map(visitor) + + } + + fn deserialize_struct<V>(self, + name: &'static str, + fields: &'static [&'static str], + visitor: V) + -> Result<V::Value> + where V: de::Visitor<'de>, + { + self.to_deserializer()?.deserialize_struct(name, fields, visitor) + } + + fn deserialize_newtype_struct<V>( + self, + _name: &'static str, + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + self.deserialize_seq(visitor) + } + + fn deserialize_tuple<V>( + self, + _len: usize, + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + // self.to_deserializer()?.deserialize_tuple(len, visitor) + self.deserialize_seq(visitor) + + } + fn deserialize_tuple_struct<V>( + self, + _name: &'static str, + _len: usize, + visitor: V + ) -> Result<V::Value> + where V: de::Visitor<'de> + { + self.deserialize_seq(visitor) + } + + deserialize_primitive!(bool, deserialize_bool, visit_bool); + deserialize_primitive!(i8, deserialize_i8, visit_i8); + deserialize_primitive!(i16, deserialize_i16, visit_i16); + deserialize_primitive!(i32, deserialize_i32, visit_i32); + deserialize_primitive!(i64, deserialize_i64, visit_i64); + deserialize_primitive!(u8, deserialize_u8, visit_u8); + deserialize_primitive!(u16, deserialize_u16, visit_u16); + deserialize_primitive!(u32, deserialize_u32, visit_u32); + deserialize_primitive!(u64, deserialize_u64, visit_u64); + deserialize_primitive!(f32, deserialize_f32, visit_f32); + deserialize_primitive!(f64, deserialize_f64, visit_f64); + + + forward_to_deserialize_any! { + char + str + string + unit + bytes + byte_buf + unit_struct + // newtype_struct + // tuple_struct + identifier + // tuple + // enum + ignored_any + } +} + + +macro_rules! forward_parsable_to_deserialize_any { + ($($ty:ident => $meth:ident,)*) => { + $( + fn $meth<V>(self, visitor: V) -> Result<V::Value> where V: de::Visitor<'de> { + match self.0.parse::<$ty>() { + Ok(val) => val.into_deserializer().$meth(visitor), + Err(e) => Err(de::Error::custom(e)) + } + } + )* + } +} + + +pub struct ParsableStringDeserializer(String); + +impl<'de> de::Deserializer<'de> for ParsableStringDeserializer { + type Error = Error; + + fn deserialize_any<V>(self, visitor: V) -> Result<V::Value> + where V: de::Visitor<'de>, + { + self.0.into_deserializer().deserialize_any(visitor) + } + + + forward_to_deserialize_any! { + // bool + // u8 + // u16 + // u32 + // u64 + // i8 + // i16 + // i32 + // i64 + // f32 + // f64 + map + struct + seq + option + char + str + string + unit + bytes + byte_buf + unit_struct + newtype_struct + tuple_struct + identifier + tuple + enum + ignored_any + } + + forward_parsable_to_deserialize_any! { + bool => deserialize_bool, + u8 => deserialize_u8, + u16 => deserialize_u16, + u32 => deserialize_u32, + u64 => deserialize_u64, + i8 => deserialize_i8, + i16 => deserialize_i16, + i32 => deserialize_i32, + i64 => deserialize_i64, + f32 => deserialize_f32, + f64 => deserialize_f64, + } + +} diff --git a/src/de/parse.rs b/src/de/parse.rs new file mode 100644 index 0000000..7a647db --- /dev/null +++ b/src/de/parse.rs @@ -0,0 +1,359 @@ +use serde::de; + +use super::*; + +/// To override the default serialization parameters, first construct a new +/// Config. +/// +/// A `max_depth` of 0 implies no nesting: the result will be a flat map. +/// This is mostly useful when the maximum nested depth is known beforehand, +/// to prevent denial of service attacks by providing incredibly deeply nested +/// inputs. +/// +/// ``` +/// use serde_qs::de::Config; +/// use std::collections::HashMap; +/// +/// let config = Config::with_max_depth(0); +/// let map: HashMap<String, String> = config.deserialize_str("a[b][c]=1") +/// .unwrap(); +/// assert_eq!(map.get("a[b][c]").unwrap(), "1"); +/// +/// let config = Config::with_max_depth(10); +/// let map: HashMap<String, HashMap<String, HashMap<String, String>>> = +/// config.deserialize_str("a[b][c]=1").unwrap(); +/// assert_eq!(map.get("a").unwrap().get("b").unwrap().get("c").unwrap(), "1"); +/// ``` +/// +pub struct Config { + /// Specifies the maximum depth key that `serde_qs` will attempt to + /// deserialize. Default is 5. + max_depth: usize, +} + +impl Default for Config { + fn default() -> Self { + Config { max_depth: 5 } + } +} + +impl Config { + pub fn with_max_depth(depth: usize) -> Config { + Config { + max_depth: depth + } + } + + pub fn max_depth(&self) -> usize { + self.max_depth + } +} + +impl Config { + pub fn deserialize_bytes<'de, T: de::Deserialize<'de>>(&self, + input: &[u8]) + -> Result<T> { + T::deserialize(Deserializer::with_config(self, input)) + } + + pub fn deserialize_str<'de, T: de::Deserialize<'de>>(&self, + input: &str) + -> Result<T> { + self.deserialize_bytes(input.as_bytes()) + } + + pub fn deserialize_reader<'de, T, R>(&self, mut reader: R) -> Result<T> + where T: de::Deserialize<'de>, + R: Read, + { + let mut buf = vec![]; + reader.read_to_end(&mut buf) + .map_err(|e| { + ErrorKind::Io(e) + })?; + self.deserialize_bytes(&buf) + } +} + + +macro_rules! tu { + ($x:expr) => ( + match $x { + Some(x) => x, + None => return Err( + de::Error::custom("query string ended before expected")) + } + ) +} + +use std::iter::Iterator; +use std::str; + +pub struct Parser<I: Iterator<Item = u8>> { + inner: I, + acc: Vec<u8>, + peeked: Option<u8>, + depth: usize, +} + +impl<I: Iterator<Item = u8>> Iterator for Parser<I> { + type Item = u8; + #[inline] + fn next(&mut self) -> Option<Self::Item> { + self.inner.next() + } +} + + +fn insert_into_map(node: &mut Level, key: String, value: String) { + if let Level::Nested(ref mut map) = *node { + match map.entry(key) { + Entry::Occupied(mut o) => { + o.insert(Level::Invalid("Multiple values for one key")); + }, + Entry::Vacant(vm) => { + vm.insert(Level::Flat(value)); + }, + } + } else { + let mut map = BTreeMap::default(); + map.insert(key, Level::Flat(value)); + *node = Level::Nested(map); + } +} + +impl<I: Iterator<Item = u8>> Parser<I> { + pub fn new(inner: I, acc: Vec<u8>, peeked: Option<u8>, depth: usize) -> Self { + Parser { + inner, acc, peeked, depth + } + } + + pub fn to_deserializer(mut self) -> Deserializer { + let map = BTreeMap::default(); + let mut root = Level::Nested(map); + while let Ok(x) = self.parse(&mut root) { + if !x { + break; + } + } + let iter = match root { + Level::Nested(map) => map.into_iter(), + _ => panic!(""), + }; + Deserializer { + iter: iter, + value: None, + } + } + + #[inline] + fn peek(&mut self) -> Option<<Self as Iterator>::Item> { + if !self.acc.is_empty() { + self.peeked + } else if let Some(x) = self.inner.next() { + self.acc.push(x); + self.peeked = Some(x); + Some(x) + } else { + None + } + } + + fn parse_key(&mut self, + end_on: u8, + consume: bool) + -> Result<String> { + loop { + if let Some(x) = self.next() { + match x { + x if x == end_on => { + let res = String::from_utf8(self.acc.split_off(0)); + self.acc.clear(); + + // Add this character back to the buffer for peek. + if !consume { + self.acc.push(x); + self.peeked = Some(x); + } + return res.map_err(|_| de::Error::custom("blah")); + }, + b'=' => { + // Allow the '=' byte when parsing keys within [] + if end_on == b']' { + self.acc.push(b'='); + } else { + let res = String::from_utf8(self.acc.split_off(0)); + self.acc.clear(); + + // Add this character back to the buffer for peek. + self.acc.push(b'='); + self.peeked = Some(b'='); + + return res.map_err(|_| de::Error::custom("blah")); + } + }, + b' ' => { + self.acc.push(b' '); + }, + b'&' => { + let res = String::from_utf8(self.acc.split_off(0)); + self.acc.clear(); + self.acc.push(b'&'); + self.peeked = Some(b'&'); + return res.map_err(|_| de::Error::custom("blah")); + }, + x @ 0x20...0x7e => { + self.acc.push(x); + }, + _ => { + return Err(de::Error::custom("unexpected character \ + in query string.")); + }, + } + } else { + // End of string. + let res = String::from_utf8(self.acc.split_off(0)); + self.acc.clear(); + return res.map_err(|_| de::Error::custom("blah")); + } + } + } + + fn parse_map_value(&mut self, + key: String, + node: &mut Level) + -> Result<()> { + if let Some(x) = self.peek() { + match x { + b'=' => { + self.acc.clear(); + for b in self.inner.by_ref().take_while(|b| b != &b'&') { + if b == b'+' { + self.acc.push(b' '); + } else { + self.acc.push(b); + } + } + let value = String::from_utf8(self.acc.split_off(0)); + let value = value.map_err(|e| ErrorKind::Utf8(e))?; + // Reached the end of the key string + insert_into_map(node, key, value); + Ok(()) + }, + b'&' => { + insert_into_map(node, key, "".to_string()); + Ok(()) + }, + b'[' => { + if let Level::Invalid(_) = *node { + *node = Level::Nested(BTreeMap::default()); + } + if let Level::Nested(ref mut map) = *node { + self.depth -= 1; + self.parse(map.entry(key) + .or_insert(Level::Invalid("uninitialised")))?; + Ok(()) + } else { + Err(de::Error::custom(format!("tried to insert a \ + new key into {:?}", + node))) + } + }, + _ => { + panic!("Unexpected character"); + }, + } + } else { + insert_into_map(node, key, "".to_string()); + Ok(()) + } + } + + fn parse_seq_value(&mut self, node: &mut Level) -> Result<()> { + match tu!(self.peek()) { + b'=' => { + self.acc.clear(); + for b in self.inner.by_ref().take_while(|b| b != &b'&') { + self.acc.push(b); + } + let value = String::from_utf8(self.acc.split_off(0)) + .map(|s| s.into()); + let value = value.map_err(|e| ErrorKind::Utf8(e))?; + // Reached the end of the key string + if let Level::Sequence(ref mut seq) = *node { + seq.push(Level::Flat(value)); + } else { + let mut seq = Vec::new(); + seq.push(Level::Flat(value)); + *node = Level::Sequence(seq); + } + Ok(()) + }, + _ => { + Err(de::Error::custom("non-indexed sequence of structs not \ + supported")) + }, + } + } + + + pub fn parse(&mut self, node: &mut Level) -> Result<bool> { + // First character determines parsing type + if self.depth == 0 { + let key = self.parse_key(b'\x00', true)?; + self.parse_map_value(key.into(), node)?; + self.depth += 1; + return Ok(true); + } + match self.peek() { + Some(x) => { + match x { + b'[' => { + self.acc.clear(); + // let _ = self.next(); + match tu!(self.peek()) { + // key is of the form "[...", not really allowed. + b'[' => { + panic!(""); + + }, + // key is simply "[]", so treat as a seq. + b']' => { + self.acc.clear(); + self.parse_seq_value(node)?; + self.depth += 1; + Ok(true) + + }, + // Key is "[a..." so parse up to the closing "]" + 0x20...0x7e => { + let key = self.parse_key(b']', true)?; + self.parse_map_value(key.into(), node)?; + self.depth += 1; + Ok(true) + + }, + _ => { + panic!(""); + }, + } + }, + // This means the key should be a root key + // of the form "abc" or "abc[...]" + 0x20...0x7e => { + let key = self.parse_key(b'[', false)?; + self.parse_map_value(key.into(), node)?; + self.depth += 1; + Ok(true) + }, + _ => { + panic!(""); + }, + } + }, + // Ran out of characters to parse + None => Ok(false), + } + } +} |