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
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
use serde::{
    self,
    de::{Deserializer, MapAccess, Visitor},
    Deserialize,
};
use std::{fmt, marker::PhantomData};

pub trait FromKeyValue {
    type Key;
    type Value;

    fn from_key_value(key: Self::Key, value: Self::Value) -> Self;
}

pub struct KeyValueVecMap<T: FromKeyValue>(pub Vec<T>);

impl<T: FromKeyValue> Into<Vec<T>> for KeyValueVecMap<T> {
    fn into(self) -> Vec<T> {
        self.0
    }
}

struct KeyValueVecMapVisitor<T: FromKeyValue> {
    marker: PhantomData<fn() -> KeyValueVecMap<T>>,
}

impl<T: FromKeyValue> KeyValueVecMapVisitor<T> {
    fn new() -> Self {
        Self {
            marker: PhantomData,
        }
    }
}

impl<'de, T: FromKeyValue, K, V> Visitor<'de> for KeyValueVecMapVisitor<T>
where
    T: FromKeyValue<Key = K, Value = V>,
    K: Deserialize<'de>,
    V: Deserialize<'de>,
{
    type Value = KeyValueVecMap<T>;

    fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
        formatter.write_str("key value map")
    }

    fn visit_map<M>(self, mut access: M) -> Result<Self::Value, M::Error>
    where
        M: MapAccess<'de>,
    {
        let mut vec = Vec::with_capacity(access.size_hint().unwrap_or(0));

        while let Some((key, value)) = access.next_entry()? {
            vec.push(T::from_key_value(key, value));
        }

        Ok(KeyValueVecMap(vec))
    }
}

impl<'de, T, K, V> Deserialize<'de> for KeyValueVecMap<T>
where
    T: FromKeyValue<Key = K, Value = V>,
    K: Deserialize<'de>,
    V: Deserialize<'de>,
{
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
    where
        D: Deserializer<'de>,
    {
        deserializer.deserialize_map(KeyValueVecMapVisitor::new())
    }
}

#[test]
fn test_deserialize() {
    let json = r#"
        {
            "temperature": 40,
            "pressure": 123
        }
    "#;

    #[derive(Debug, Eq, PartialEq)]
    struct SingleMeasurement {
        name: String,
        value: u32,
    }

    impl FromKeyValue for SingleMeasurement {
        type Key = String;
        type Value = u32;
        fn from_key_value(key: Self::Key, value: Self::Value) -> Self {
            Self { name: key, value }
        }
    }

    let values: Vec<SingleMeasurement> =
        serde_json::from_str::<KeyValueVecMap<SingleMeasurement>>(json)
            .unwrap()
            .into();

    assert_eq!(
        values,
        vec![
            SingleMeasurement {
                name: "temperature".into(),
                value: 40
            },
            SingleMeasurement {
                name: "pressure".into(),
                value: 123
            },
        ]
    );
}