jsonrustserializationserde

How to deserialize a Map with custom value type in serde?


I have the following json file that I want to deserialize in a Rust struct:

{
  "name": "Manuel",
  "friends": {
    "id1": 1703692376,
    ...
  } 
  ...
}

The friends tag contains the ids and a timestamp I created a Rust struct like this:

use std::collections::HashMap;
use serde::{Deserialize, Serialize};
#[derive(Debug,Clone,Serialize,Deserialize)]
pub struct MyStruct{
    name: String,
    friends: HashMap<String, i64>
}

And that works fine, but I would actually like to have something like this:

use std::collections::HashMap;
use serde::{Deserialize, Serialize};
#[derive(Debug,Clone,Serialize,Deserialize)]
pub struct MyStruct{
    name: String,
    friends: HashMap<String, SystemTime>
}

So I would like to transform the integer value to a SystemTime type. Is it possible to do that with serde?


Solution

  • serde_with has got you covered. It supports de/serialization of SystemTime from various formats, including seconds since epoch, and unlike #[serde(with)], it supports nested types:

    #[serde_with::serde_as]
    #[derive(Debug, Clone, Serialize, Deserialize)]
    pub struct MyStruct {
        name: String,
        #[serde_as(as = "HashMap<_, serde_with::TimestampSeconds>")]
        friends: HashMap<String, SystemTime>,
    }