use alloc::{string::String, vec::Vec}; use chrono::NaiveDateTime; use password_hash::Key; use serde::{Deserialize, Serialize}; use slint::SharedString; use spectre_api_sys::{SpectreAlgorithm, SpectreCounter, SpectreResultType}; #[derive(Deserialize, Serialize, Default, Clone, Debug, PartialEq, Eq)] pub struct SpectreUsersConfig { pub users: Vec, } #[derive(Deserialize, Serialize, Clone, Debug, PartialEq, Eq)] pub struct SpectreUserConfig { pub username: SharedString, #[serde(with = "serde_bytes")] pub encrypted_key: Key, #[serde(with = "serde_bytes")] pub key_id: [u8; 32], } #[derive(Deserialize, Serialize, Clone, Debug, PartialEq, Eq)] pub struct SpectreSiteConfig { #[serde(with = "with_repr")] pub algorithm: SpectreAlgorithm, pub counter: SpectreCounter::Type, #[serde(rename = "type")] #[serde(with = "with_repr")] pub result_type: SpectreResultType, pub password: Option, #[serde(with = "with_repr")] pub login_type: SpectreResultType, pub login_name: Option, pub uses: u32, pub last_used: NaiveDateTime, } impl Default for SpectreSiteConfig { fn default() -> Self { Self { algorithm: SpectreAlgorithm::Current, counter: SpectreCounter::Default, result_type: SpectreResultType::SpectreResultDefaultResult, password: None, login_type: SpectreResultType::SpectreResultDefaultLogin, login_name: None, uses: 0, last_used: Default::default(), } } } #[derive(Clone, Debug, PartialEq, Eq)] pub struct SpectreSite { pub username: SharedString, pub site_name: SharedString, pub config: SpectreSiteConfig, } mod with_repr { use serde::{Deserialize, Deserializer, Serializer}; use spectre_api_sys::{SpectreAlgorithm, SpectreResultType}; pub trait ReprConvert: Copy { type Repr: Copy; fn into_repr(self) -> Self::Repr; fn from_repr(repr: Self::Repr) -> Self; } impl ReprConvert for SpectreAlgorithm { type Repr = u32; fn from_repr(repr: Self::Repr) -> Self { unsafe { core::mem::transmute::(repr) } } fn into_repr(self) -> Self::Repr { self as Self::Repr } } impl ReprConvert for SpectreResultType { type Repr = u32; fn from_repr(repr: Self::Repr) -> Self { unsafe { core::mem::transmute::(repr) } } fn into_repr(self) -> Self::Repr { self as Self::Repr } } #[allow(unused)] pub fn serialize(value: &T, serializer: S) -> Result where T: ReprConvert, S: Serializer, { serializer.serialize_u32(value.into_repr()) } #[allow(unused)] pub fn deserialize<'de, T, D>(deserializer: D) -> Result where T: ReprConvert, D: Deserializer<'de>, { ::deserialize(deserializer).map(T::from_repr) } }