【问题标题】:Is it possible to flatten sub-object fields while parsing with serde_json?使用 serde_json 解析时是否可以展平子对象字段?
【发布时间】:2016-12-08 15:15:58
【问题描述】:

#[serde(rename)] 似乎是正确的选择,但文档没有说明是否可能或如何做到这一点。

这个 JSON 对象:

{
   "name" : "myobject"
   "info" : 
   {
      "counter" : "3"
      "foo" : "bar"
   }
}

对应的 flat Rust 结构应该是:

#[derive(Deserialize)]
struct Object {
    name: String,
    #[serde(rename="info.counter")] // wrong syntax here !!
    count: i32,
    #[serde(rename="info::foo")] // neither this works
    foo: String,
}

【问题讨论】:

标签: json rust serde


【解决方案1】:

没有内置的方法可以使用属性执行此操作,但您可以为您的 Object 类型编写自己的 Deserialize impl,该类型首先反序列化为一些中间帮助器表示,然后将数据重新排列到所需的结构中。

#[macro_use]
extern crate serde_derive;

extern crate serde;
extern crate serde_json;

use serde::{Deserialize, Deserializer};

#[derive(Debug)]
struct Object {
    name: String,
    count: i32,
    foo: String,
}

impl<'de> Deserialize<'de> for Object {
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
        where D: Deserializer<'de>
    {
        #[derive(Deserialize)]
        struct Outer {
            name: String,
            info: Inner,
        }

        #[derive(Deserialize)]
        struct Inner {
            count: i32,
            foo: String,
        }

        let helper = Outer::deserialize(deserializer)?;
        Ok(Object {
            name: helper.name,
            count: helper.info.count,
            foo: helper.info.foo,
        })
    }
}

fn main() {
    let j = r#"{
                 "name": "myobject",
                 "info": {
                   "count": 3,
                   "foo": "bar"
                 }
               }"#;

    println!("{:#?}", serde_json::from_str::<Object>(j).unwrap());
}

输出是:

Object {
    name: "myobject",
    count: 3,
    foo: "bar"
}

在三个本质上不同的地方会出现微不足道的嵌套:

  1. 与其他字段相邻
  2. 单独在顶层
  3. 单独在顶层之下

这三个都需要不同的方法。在这个问题中观察到 #1。

要解决 #2 或 #3,请参阅 Is there a way to omit wrapper/root objects when deserializing objects with Serde?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-02-14
    • 2020-05-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-10-02
    • 2022-11-10
    • 2023-02-07
    相关资源
    最近更新 更多