pub mod property_map; pub use property_map::PropertyMap; use std::fmt::{Debug, Formatter, Write}; use chrono::{DateTime, Utc}; use multimap::MultiMap; use oauth2::RefreshToken; use serde::{Deserialize, Deserializer, Serialize}; use serde::de::{Error, SeqAccess, Visitor}; use uuid::Uuid; #[derive(Debug, Serialize, Deserialize)] pub struct Property { pub name: String, pub value: String, pub signature: Option } #[derive(Debug, Serialize, Deserialize)] pub struct PlayerProfile { #[serde(with = "uuid::serde::simple")] pub id: Uuid, pub name: String, #[serde(default, skip_serializing_if = "MultiMap::is_empty", with = "property_map")] pub properties: MultiMap } #[derive(Serialize, Deserialize)] pub(super) struct Token { pub value: String, #[serde(skip_serializing_if = "Option::is_none")] pub expire: Option> } struct RedactedValue; impl Debug for RedactedValue { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { f.write_str("[redacted]") } } impl Debug for Token { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { f.debug_struct("Token") .field("value", &RedactedValue) .field("expire", &self.expire) .finish() } } #[derive(Debug, Deserialize)] #[serde(rename_all = "UPPERCASE")] pub enum SkinState { Active, Inactive } #[derive(Debug, Deserialize)] #[serde(rename_all = "UPPERCASE")] pub enum SkinVariant { Classic, Slim } #[derive(Debug, Deserialize)] #[serde(rename_all = "camelCase")] pub struct SkinInfo { pub id: Uuid, pub state: SkinState, pub url: String, pub texture_key: Option, pub variant: Option, pub alias: Option } #[derive(Debug, Deserialize)] #[serde(rename_all = "camelCase")] pub struct MinecraftPlayerInfo { #[serde(with = "uuid::serde::simple")] pub id: Uuid, pub name: String, #[serde(default)] pub skins: Vec, #[serde(default)] pub capes: Vec, #[serde(default)] pub demo: bool, #[serde(default)] pub legacy: bool, // todo: profile actions (idk the format) } #[derive(Debug, Serialize, Deserialize)] pub struct MsaUser { #[serde(skip_serializing_if = "Option::is_none")] pub player_profile: Option, pub xuid: Option, pub gamertag: Option, #[serde(skip)] // this information is transient pub player_info: Option, pub(super) client_id: oauth2::ClientId, #[serde(default, skip_serializing_if = "std::ops::Not::not")] pub(super) is_azure_client_id: bool, pub(super) mc_token: Option, pub(super) xbl_token: Option, pub(super) refresh_token: Option } #[derive(Debug, Serialize, Deserialize)] #[serde(tag = "type")] pub enum User { Dummy(PlayerProfile), MSA(MsaUser) } #[derive(Debug, Serialize, Deserialize)] pub struct AuthenticationDatabase { pub users: Vec }