systemprompt_users/services/
admin_service.rs1use systemprompt_identifiers::UserId;
2
3use crate::error::Result;
4use crate::models::{User, UserRole};
5use crate::UserService;
6
7#[derive(Debug)]
8pub struct UserAdminService {
9 user_service: UserService,
10}
11
12impl UserAdminService {
13 pub const fn new(user_service: UserService) -> Self {
14 Self { user_service }
15 }
16
17 pub async fn find_user(&self, identifier: &str) -> Result<Option<User>> {
18 if uuid::Uuid::parse_str(identifier).is_ok() {
19 let user_id = UserId::new(identifier);
20 if let Some(user) = self.user_service.find_by_id(&user_id).await? {
21 return Ok(Some(user));
22 }
23 }
24
25 if identifier.contains('@') {
26 return self.user_service.find_by_email(identifier).await;
27 }
28
29 self.user_service.find_by_name(identifier).await
30 }
31
32 pub async fn promote_to_admin(&self, user_identifier: &str) -> Result<PromoteResult> {
33 let user = self.find_user(user_identifier).await?;
34 let admin_role = UserRole::Admin.as_str().to_string();
35 let user_role = UserRole::User.as_str().to_string();
36
37 match user {
38 Some(u) => {
39 let current_roles = u.roles.clone();
40
41 if current_roles.contains(&admin_role) {
42 return Ok(PromoteResult::AlreadyAdmin(u));
43 }
44
45 let mut new_roles = current_roles;
46 if !new_roles.contains(&admin_role) {
47 new_roles.push(admin_role);
48 }
49 if !new_roles.contains(&user_role) {
50 new_roles.push(user_role);
51 }
52
53 let updated = self.user_service.assign_roles(&u.id, &new_roles).await?;
54 Ok(PromoteResult::Promoted(updated, new_roles))
55 },
56 None => Ok(PromoteResult::UserNotFound),
57 }
58 }
59
60 pub async fn demote_from_admin(&self, user_identifier: &str) -> Result<DemoteResult> {
61 let user = self.find_user(user_identifier).await?;
62 let admin_role = UserRole::Admin.as_str();
63 let user_role = UserRole::User.as_str().to_string();
64
65 match user {
66 Some(u) => {
67 let current_roles = u.roles.clone();
68
69 if !current_roles.contains(&admin_role.to_string()) {
70 return Ok(DemoteResult::NotAdmin(u));
71 }
72
73 let new_roles: Vec<String> = current_roles
74 .into_iter()
75 .filter(|r| r != admin_role)
76 .collect();
77
78 let mut final_roles = new_roles;
79 if !final_roles.contains(&user_role) {
80 final_roles.push(user_role);
81 }
82
83 let updated = self.user_service.assign_roles(&u.id, &final_roles).await?;
84 Ok(DemoteResult::Demoted(updated, final_roles))
85 },
86 None => Ok(DemoteResult::UserNotFound),
87 }
88 }
89}
90
91#[derive(Debug)]
92pub enum PromoteResult {
93 Promoted(User, Vec<String>),
94 AlreadyAdmin(User),
95 UserNotFound,
96}
97
98#[derive(Debug)]
99pub enum DemoteResult {
100 Demoted(User, Vec<String>),
101 NotAdmin(User),
102 UserNotFound,
103}