cyberdrop_client/
account.rs1use serde::{Deserialize, Serialize};
2
3use crate::CyberdropError;
4use crate::client::CyberdropClient;
5use crate::token::AuthToken;
6
7#[derive(Debug, Clone, PartialEq, Eq, Deserialize)]
9pub struct Permissions {
10 pub user: bool,
12 pub poweruser: bool,
14 pub moderator: bool,
16 pub admin: bool,
18 pub superadmin: bool,
20}
21
22#[derive(Debug, Clone, PartialEq, Eq)]
24pub struct TokenVerification {
25 pub success: bool,
27 pub username: String,
29 pub permissions: Permissions,
31}
32
33#[derive(Debug, Serialize)]
34pub(crate) struct LoginRequest {
35 pub(crate) username: String,
36 pub(crate) password: String,
37}
38
39#[derive(Debug, Deserialize)]
40pub(crate) struct LoginResponse {
41 pub(crate) token: Option<AuthToken>,
42}
43
44#[derive(Debug, Serialize)]
45pub(crate) struct RegisterRequest {
46 pub(crate) username: String,
47 pub(crate) password: String,
48}
49
50#[derive(Debug, Deserialize)]
51pub(crate) struct RegisterResponse {
52 pub(crate) success: Option<bool>,
53 pub(crate) token: Option<AuthToken>,
54 pub(crate) message: Option<String>,
55 pub(crate) description: Option<String>,
56}
57
58#[derive(Debug, Serialize)]
59pub(crate) struct VerifyTokenRequest {
60 pub(crate) token: String,
61}
62
63#[derive(Debug, Deserialize)]
64pub(crate) struct VerifyTokenResponse {
65 pub(crate) success: Option<bool>,
66 pub(crate) username: Option<String>,
67 pub(crate) permissions: Option<Permissions>,
68}
69
70impl CyberdropClient {
71 pub async fn login(
81 &self,
82 username: impl Into<String>,
83 password: impl Into<String>,
84 ) -> Result<AuthToken, CyberdropError> {
85 let payload = LoginRequest {
86 username: username.into(),
87 password: password.into(),
88 };
89
90 let response: LoginResponse = self.post_json("api/login", &payload, false).await?;
91 response.token.ok_or(CyberdropError::MissingToken)
92 }
93
94 pub async fn register(
107 &self,
108 username: impl Into<String>,
109 password: impl Into<String>,
110 ) -> Result<AuthToken, CyberdropError> {
111 let payload = RegisterRequest {
112 username: username.into(),
113 password: password.into(),
114 };
115
116 let response: RegisterResponse = self.post_json("api/register", &payload, false).await?;
117
118 if response.success.unwrap_or(false) {
119 return response.token.ok_or(CyberdropError::MissingToken);
120 }
121
122 let msg = response
123 .description
124 .or(response.message)
125 .unwrap_or_else(|| "registration failed".to_string());
126
127 Err(CyberdropError::Api(msg))
128 }
129
130 pub async fn verify_token(
141 &self,
142 token: impl Into<String>,
143 ) -> Result<TokenVerification, CyberdropError> {
144 let payload = VerifyTokenRequest {
145 token: token.into(),
146 };
147
148 let response: VerifyTokenResponse =
149 self.post_json("api/tokens/verify", &payload, false).await?;
150
151 let success = response.success.ok_or(CyberdropError::MissingField(
152 "verification response missing success",
153 ))?;
154 let username = response.username.ok_or(CyberdropError::MissingField(
155 "verification response missing username",
156 ))?;
157 let permissions = response.permissions.ok_or(CyberdropError::MissingField(
158 "verification response missing permissions",
159 ))?;
160
161 Ok(TokenVerification {
162 success,
163 username,
164 permissions,
165 })
166 }
167}