Skip to content

Commit

Permalink
Merge pull request #9 from clouds56/patch-2
Browse files Browse the repository at this point in the history
split deserialize_seq
  • Loading branch information
zrkn authored Jan 31, 2020
2 parents 0df32c7 + 2b0dce2 commit a156522
Showing 1 changed file with 74 additions and 14 deletions.
88 changes: 74 additions & 14 deletions src/de.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,17 +23,7 @@ impl<'lua, 'de> serde::Deserializer<'de> for Deserializer<'lua> {
Value::Integer(v) => visitor.visit_i64(v),
Value::Number(v) => visitor.visit_f64(v),
Value::String(v) => visitor.visit_str(v.to_str()?),
Value::Table(v) => if v.contains_key(1)? {
let len = v.len()? as usize;
let mut deserializer = SeqDeserializer(v.sequence_values());
let seq = visitor.visit_seq(&mut deserializer)?;
let remaining = deserializer.0.count();
if remaining == 0 {
Ok(seq)
} else {
Err(serde::de::Error::invalid_length(len, &"fewer elements in array"))
}
} else {
Value::Table(v) => {
let len = v.len()? as usize;
let mut deserializer = MapDeserializer(v.pairs(), None);
let map = visitor.visit_map(&mut deserializer)?;
Expand Down Expand Up @@ -90,10 +80,44 @@ impl<'lua, 'de> serde::Deserializer<'de> for Deserializer<'lua> {
visitor.visit_enum(EnumDeserializer { variant, value })
}

#[inline]
fn deserialize_seq<V>(self, visitor: V) -> Result<V::Value>
where V: serde::de::Visitor<'de>
{
match self.value {
Value::Table(v) => {
let len = v.len()? as usize;
let mut deserializer = SeqDeserializer(v.sequence_values());
let seq = visitor.visit_seq(&mut deserializer)?;
let remaining = deserializer.0.count();
if remaining == 0 {
Ok(seq)
} else {
Err(serde::de::Error::invalid_length(len, &"fewer elements in array"))
}
}
_ => Err(serde::de::Error::custom("invalid value type")),
}
}

#[inline]
fn deserialize_tuple<V>(self, _len: usize, visitor: V) -> Result<V::Value>
where V: serde::de::Visitor<'de>
{
self.deserialize_seq(visitor)
}

#[inline]
fn deserialize_tuple_struct<V>(self, _name: &'static str, _len: usize, visitor: V) -> Result<V::Value>
where V: serde::de::Visitor<'de>
{
self.deserialize_seq(visitor)
}

forward_to_deserialize_any! {
bool i8 i16 i32 i64 u8 u16 u32 u64 f32 f64 char str string bytes
byte_buf unit unit_struct newtype_struct seq tuple
tuple_struct map struct identifier ignored_any
byte_buf unit unit_struct newtype_struct
map struct identifier ignored_any
}
}

Expand Down Expand Up @@ -253,23 +277,59 @@ mod tests {
struct Test {
int: u32,
seq: Vec<String>,
map: std::collections::HashMap<i32, i32>,
empty: Vec<()>,
}

let expected = Test { int: 1, seq: vec!["a".to_owned(), "b".to_owned()] };
let expected = Test {
int: 1,
seq: vec!["a".to_owned(), "b".to_owned()],
map: vec![(1, 2), (4, 1)].into_iter().collect(),
empty: vec![]
};

println!("{:?}", expected);
let lua = Lua::new();
lua.context(|lua| {
let value = lua.load(r#"
a = {}
a.int = 1
a.seq = {"a", "b"}
a.map = {2, [4]=1}
a.empty = {}
return a
"#).eval().unwrap();
let got = from_value(value).unwrap();
assert_eq!(expected, got);
});
}

#[test]
fn test_tuple() {
#[derive(Deserialize, PartialEq, Debug)]
struct Rgb(u8, u8, u8);

let lua = Lua::new();
lua.context(|lua| {
let expected = Rgb(1, 2, 3);
let value = lua.load(
r#"
a = {1, 2, 3}
return a
"#).eval().unwrap();
let got = from_value(value).unwrap();
assert_eq!(expected, got);

let expected = (1, 2, 3);
let value = lua.load(
r#"
a = {1, 2, 3}
return a
"#).eval().unwrap();
let got = from_value(value).unwrap();
assert_eq!(expected, got);
});
}

#[test]
fn test_enum() {
Expand Down

0 comments on commit a156522

Please sign in to comment.