1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
use std::error;
use std::fmt::{self, Display, Formatter};

use serde::de::Unexpected;

use {Integer, IntPriv, Value, ValueRef};

pub use self::de::{deserialize_from, from_value, EnumRefDeserializer};
pub use self::se::to_value;

mod de;
mod se;

#[derive(Debug)]
pub enum Error {
    Syntax(String),
}

impl Display for Error {
    fn fmt(&self, fmt: &mut Formatter) -> Result<(), fmt::Error> {
        match *self {
            Error::Syntax(ref err) => write!(fmt, "{}: {}", error::Error::description(self), err)
        }
    }
}

impl error::Error for Error {
    fn description(&self) -> &str {
        "error while decoding value"
    }

    fn cause(&self) -> Option<&error::Error> {
        match *self {
            Error::Syntax(..) => None,
        }
    }
}

trait ValueExt {
    fn unexpected(&self) -> Unexpected;
}

impl ValueExt for Value {
    fn unexpected(&self) -> Unexpected {
        match *self {
            Value::Nil => Unexpected::Unit,
            Value::Boolean(v) => Unexpected::Bool(v),
            Value::Integer(Integer { n }) => {
                match n {
                    IntPriv::PosInt(v) => Unexpected::Unsigned(v),
                    IntPriv::NegInt(v) => Unexpected::Signed(v),
                }
            }
            Value::F32(v) => Unexpected::Float(v as f64),
            Value::F64(v) => Unexpected::Float(v),
            Value::String(ref v) => {
                match v.s {
                    Ok(ref v) => Unexpected::Str(v),
                    Err(ref v) => Unexpected::Bytes(&v.0[..]),
                }
            }
            Value::Binary(ref v) => Unexpected::Bytes(v),
            Value::Array(..) => Unexpected::Seq,
            Value::Map(..) => Unexpected::Map,
            Value::Ext(..) => Unexpected::Seq,
        }
    }
}

impl<'a> ValueExt for ValueRef<'a> {
    fn unexpected(&self) -> Unexpected {
        match *self {
            ValueRef::Nil => Unexpected::Unit,
            ValueRef::Boolean(v) => Unexpected::Bool(v),
            ValueRef::Integer(Integer { n }) => {
                match n {
                    IntPriv::PosInt(v) => Unexpected::Unsigned(v),
                    IntPriv::NegInt(v) => Unexpected::Signed(v),
                }
            }
            ValueRef::F32(v) => Unexpected::Float(v as f64),
            ValueRef::F64(v) => Unexpected::Float(v),
            ValueRef::String(ref v) => {
                match v.s {
                    Ok(ref v) => Unexpected::Str(v),
                    Err(ref v) => Unexpected::Bytes(&v.0[..]),
                }
            }
            ValueRef::Binary(ref v) => Unexpected::Bytes(v),
            ValueRef::Array(..) => Unexpected::Seq,
            ValueRef::Map(..) => Unexpected::Map,
            ValueRef::Ext(..) => Unexpected::Seq,
        }
    }
}