threescalers/response/
app_keys_list.rs

1use std::prelude::v1::*;
2
3use std::fmt;
4
5use serde::{
6    de::{Deserializer, MapAccess, Visitor},
7    Deserialize,
8};
9
10use crate::{
11    application::{AppId, AppKey},
12    credentials::ServiceId,
13};
14
15#[derive(Debug, Clone, PartialEq, Eq)]
16pub struct ListAppKeys {
17    service_id: Option<ServiceId>,
18    app_id: Option<AppId>,
19    keys: Vec<AppKey>,
20}
21
22impl ListAppKeys {
23    pub fn new<S: Into<ServiceId>, A: Into<AppId>, K: Into<AppKey>, I: IntoIterator<Item = K>>(
24        service_id: Option<S>,
25        app_id: Option<A>,
26        keys: I,
27    ) -> Self {
28        Self {
29            service_id: service_id.map(Into::into),
30            app_id: app_id.map(Into::into),
31            keys: keys.into_iter().map(Into::into).collect(),
32        }
33    }
34
35    pub fn service_id(&self) -> Option<&ServiceId> {
36        self.service_id.as_ref()
37    }
38
39    pub fn app_id(&self) -> Option<&AppId> {
40        self.app_id.as_ref()
41    }
42
43    pub fn keys(&self) -> &[AppKey] {
44        self.keys.as_slice()
45    }
46}
47
48struct ListAppKeysVisitor;
49
50impl<'de> Visitor<'de> for ListAppKeysVisitor {
51    type Value = ListAppKeys;
52
53    fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
54        formatter.write_str("a structure that represents the application's keys")
55    }
56
57    fn visit_map<V>(self, mut map: V) -> Result<Self::Value, V::Error>
58    where
59        V: MapAccess<'de>,
60    {
61        #[derive(Debug, Deserialize)]
62        struct AppKeyWithId {
63            id: String,
64        }
65
66        let mut app_id: Option<AppId> = None;
67        let mut service_id: Option<ServiceId> = None;
68        // the usual maximum capacity is 5 entries
69        let mut keys: Vec<AppKey> = Vec::with_capacity(5);
70
71        while let Some(ref attr) = map.next_key::<String>()? {
72            match attr.as_str() {
73                "app" => {
74                    app_id = Some(map.next_value::<String>()?.into());
75                }
76                "svc" => {
77                    service_id = Some(map.next_value::<String>()?.into());
78                }
79                "key" => {
80                    let appkeyid = map.next_value::<AppKeyWithId>()?;
81                    keys.push(AppKey::from(appkeyid.id));
82                }
83                // unknown keys are just ignored
84                _ => (),
85            }
86        }
87
88        let list_app_keys = ListAppKeys::new(service_id, app_id, keys);
89
90        Ok(list_app_keys)
91    }
92}
93
94impl<'de> Deserialize<'de> for ListAppKeys {
95    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
96    where
97        D: Deserializer<'de>,
98    {
99        deserializer.deserialize_any(ListAppKeysVisitor)
100    }
101}