1
0
mirror of https://github.com/actix/examples synced 2025-03-27 21:44:02 +01:00
examples/simple-auth-server/src/register_handler.rs

66 lines
2.3 KiB
Rust

use actix_web::{error::BlockingError, web, HttpResponse};
use diesel::prelude::*;
use futures::Future;
use crate::errors::ServiceError;
use crate::models::{Invitation, Pool, SlimUser, User};
use crate::utils::hash_password;
// UserData is used to extract data from a post request by the client
#[derive(Debug, Deserialize)]
pub struct UserData {
pub password: String,
}
pub fn register_user(
invitation_id: web::Path<String>,
user_data: web::Json<UserData>,
pool: web::Data<Pool>,
) -> impl Future<Item = HttpResponse, Error = ServiceError> {
web::block(move || {
query(
invitation_id.into_inner(),
user_data.into_inner().password,
pool,
)
})
.then(|res| match res {
Ok(user) => Ok(HttpResponse::Ok().json(&user)),
Err(err) => match err {
BlockingError::Error(service_error) => Err(service_error),
BlockingError::Canceled => Err(ServiceError::InternalServerError),
},
})
}
fn query(
invitation_id: String,
password: String,
pool: web::Data<Pool>,
) -> Result<SlimUser, crate::errors::ServiceError> {
use crate::schema::invitations::dsl::{id, invitations};
use crate::schema::users::dsl::users;
let invitation_id = uuid::Uuid::parse_str(&invitation_id)?;
let conn: &PgConnection = &pool.get().unwrap();
invitations
.filter(id.eq(invitation_id))
.load::<Invitation>(conn)
.map_err(|_db_error| ServiceError::BadRequest("Invalid Invitation".into()))
.and_then(|mut result| {
if let Some(invitation) = result.pop() {
// if invitation is not expired
if invitation.expires_at > chrono::Local::now().naive_local() {
// try hashing the password, else return the error that will be converted to ServiceError
let password: String = hash_password(&password)?;
dbg!(&password);
let user = User::from_details(invitation.email, password);
let inserted_user: User =
diesel::insert_into(users).values(&user).get_result(conn)?;
dbg!(&inserted_user);
return Ok(inserted_user.into());
}
}
Err(ServiceError::BadRequest("Invalid Invitation".into()))
})
}