|
| 1 | +use crate::account_manager::helpers::account::{ActorAccount, AvailabilityFlags}; |
| 2 | +use crate::account_manager::AccountManager; |
| 3 | +use crate::apis::ApiError; |
| 4 | +use crate::auth_verifier::AccessFull; |
| 5 | +use crate::mailer::{send_plc_operation, TokenParam}; |
| 6 | +use crate::models::models::EmailTokenPurpose; |
| 7 | + |
| 8 | +#[tracing::instrument(skip_all)] |
| 9 | +async fn get_requester_did(auth: &AccessFull) -> Result<String, ApiError> { |
| 10 | + match &auth.access.credentials { |
| 11 | + None => { |
| 12 | + tracing::error!("Failed to find access credentials"); |
| 13 | + Err(ApiError::RuntimeError) |
| 14 | + } |
| 15 | + Some(res) => match &res.did { |
| 16 | + None => { |
| 17 | + tracing::error!("Failed to find did"); |
| 18 | + Err(ApiError::RuntimeError) |
| 19 | + } |
| 20 | + Some(did) => Ok(did.clone()), |
| 21 | + }, |
| 22 | + } |
| 23 | +} |
| 24 | + |
| 25 | +#[tracing::instrument(skip_all)] |
| 26 | +async fn get_account(requester_did: &str) -> Result<ActorAccount, ApiError> { |
| 27 | + let availability_flags = AvailabilityFlags { |
| 28 | + include_taken_down: Some(true), |
| 29 | + include_deactivated: Some(true), |
| 30 | + }; |
| 31 | + match AccountManager::get_account(&requester_did.to_string(), Some(availability_flags)).await { |
| 32 | + Ok(account) => match account { |
| 33 | + None => { |
| 34 | + tracing::error!("Account not found despite valid credentials"); |
| 35 | + Err(ApiError::RuntimeError) |
| 36 | + } |
| 37 | + Some(account) => Ok(account), |
| 38 | + }, |
| 39 | + Err(error) => { |
| 40 | + tracing::error!("Error getting account\n{error}"); |
| 41 | + Err(ApiError::RuntimeError) |
| 42 | + } |
| 43 | + } |
| 44 | +} |
| 45 | + |
| 46 | +#[tracing::instrument(skip_all)] |
| 47 | +async fn create_email_token(requester: &str) -> Result<String, ApiError> { |
| 48 | + match AccountManager::create_email_token( |
| 49 | + &requester.to_string(), |
| 50 | + EmailTokenPurpose::PlcOperation, |
| 51 | + ) |
| 52 | + .await |
| 53 | + { |
| 54 | + Ok(res) => Ok(res), |
| 55 | + Err(error) => { |
| 56 | + tracing::error!("Failed to create plc operation token\n{error}"); |
| 57 | + Err(ApiError::RuntimeError) |
| 58 | + } |
| 59 | + } |
| 60 | +} |
| 61 | + |
| 62 | +#[tracing::instrument(skip_all)] |
| 63 | +async fn do_plc_operation(account: &ActorAccount, token: String) -> Result<(), ApiError> { |
| 64 | + match &account.email { |
| 65 | + None => { |
| 66 | + tracing::error!("Failed to find email for account"); |
| 67 | + Err(ApiError::RuntimeError) |
| 68 | + } |
| 69 | + Some(email) => match send_plc_operation(email.clone(), TokenParam { token }).await { |
| 70 | + Ok(_) => { |
| 71 | + tracing::debug!("Successfully sent PLC Operation Email"); |
| 72 | + Ok(()) |
| 73 | + } |
| 74 | + Err(error) => { |
| 75 | + tracing::error!("Failed to send PLC Operation Token Email\n{error}"); |
| 76 | + Err(ApiError::RuntimeError) |
| 77 | + } |
| 78 | + }, |
| 79 | + } |
| 80 | +} |
| 81 | + |
| 82 | +#[rocket::post("/xrpc/com.atproto.identity.requestPlcOperationSignature")] |
| 83 | +#[tracing::instrument(skip_all)] |
| 84 | +pub async fn request_plc_operation_signature(auth: AccessFull) -> Result<(), ApiError> { |
| 85 | + let requester = get_requester_did(&auth).await?; |
| 86 | + let account = get_account(requester.as_str()).await?; |
| 87 | + let token = create_email_token(requester.as_str()).await?; |
| 88 | + do_plc_operation(&account, token).await?; |
| 89 | + |
| 90 | + Ok(()) |
| 91 | +} |
0 commit comments