use serde::Serialize;
#[derive(Serialize)]
struct MyStruct {
foo: Result<u32, String>
}
fn main() {
let m = MyStruct {
foo: Ok(43)
};
let n = MyStruct {
foo: Err("oh no!".into())
};
println!("{}", serde_json::to_string_pretty(&m).unwrap());
println!("{}", serde_json::to_string_pretty(&n).unwrap());
}
此输出(playground):
{ "foo": { "Ok": 43 } } { "foo": { "Err": "oh no!" } }
我可以修改序列化程序以为Result<T,E>
提供自定义输出吗?我想要类似的东西:
// No "Ok" field in case of Ok(T) { "foo": 43 } // Rename "Err" to "error" in case of Err(E) { "foo": { "error": "oh no!" } }
Result
序列化到所需序列的转换,因此您需要编写自定义序列化。幸运的是,它非常简单:use serde::{Serialize, Serializer, ser::SerializeMap};
struct MyStruct {
foo: Result<u32, String>
}
impl Serialize for MyStruct {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
let mut map = serializer.serialize_map(Some(1))?;
match &self.foo {
Ok(value) => map.serialize_entry("foo", &value)?,
Err(error) => map.serialize_entry("foo", &MyError { error } )?,
}
map.end()
}
}
// This is just used internally to get the nested error field
#[derive(Serialize)]
struct MyError<E> {
error: E,
}