Error handling
During serialization, the Serialize trait maps a Rust data structure into
Serde's data model and the Serializer trait maps the data model into the
output format. During deserialization, the Deserializer maps the input data
into Serde's data model and the Deserialize and Visitor traits map the
data model into the resulting data structure. Any of these steps can fail.
Serializecan fail, for example when aMutex<T>is being serialized and the mutex happens to be poisoned.Serializercan fail, for example the Serde data model allows maps with non-string keys but JSON does not.Deserializercan fail, especially if the input data is syntactically invalid.Deserializecan fail, usually because the input is the wrong type for the value it is being deserialized into.
In Serde, errors from the Serializer and Deserializer work just like they
would in any other Rust library. The crate defines an error type, public
functions return a Result with that error type, and there are variants for the
various possible failure modes.
Handling of errors from the Serialize and Deserialize, the data structure
being processed by the library, is built around the ser::Error and
de::Error traits. These traits allow the data format to expose constructors
for its error type for the data structure to use in various situations.
src/error.rs
use std;
use std::fmt::{self, Display};
use serde::{de, ser};
pub type Result<T> = std::result::Result<T, Error>;
// This is a bare-bones implementation. A real library would provide additional
// information in its error type, for example the line and column at which the
// error occurred, the byte offset into the input, or the current key being
// processed.
#[derive(Debug)]
pub enum Error {
// One or more variants that can be created by data structures through the
// `ser::Error` and `de::Error` traits. For example the Serialize impl for
// Mutex<T> might return an error because the mutex is poisoned, or the
// Deserialize impl for a struct may return an error because a required
// field is missing.
Message(String),
// Zero or more variants that can be created directly by the Serializer and
// Deserializer without going through `ser::Error` and `de::Error`. These
// are specific to the format, in this case JSON.
Eof,
Syntax,
ExpectedBoolean,
ExpectedInteger,
ExpectedString,
ExpectedNull,
ExpectedArray,
ExpectedArrayComma,
ExpectedArrayEnd,
ExpectedMap,
ExpectedMapColon,
ExpectedMapComma,
ExpectedMapEnd,
ExpectedEnum,
TrailingCharacters,
}
impl ser::Error for Error {
fn custom<T: Display>(msg: T) -> Self {
Error::Message(msg.to_string())
}
}
impl de::Error for Error {
fn custom<T: Display>(msg: T) -> Self {
Error::Message(msg.to_string())
}
}
impl Display for Error {
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
match self {
Error::Message(msg) => formatter.write_str(msg),
Error::Eof => formatter.write_str("unexpected end of input"),
/* and so forth */
}
}
}
impl std::error::Error for Error {}