Add get_person route
This commit is contained in:
parent
7770ab958a
commit
d2a94b078c
8 changed files with 164 additions and 12 deletions
|
|
@ -4,7 +4,7 @@ use common::adaptor::Adaptor;
|
|||
pub enum ApiError<A: Adaptor> {
|
||||
AdaptorError(A::Error),
|
||||
NotFound,
|
||||
// NotAuthorized,
|
||||
NotAuthorized,
|
||||
}
|
||||
|
||||
// Define what the error types above should return
|
||||
|
|
@ -16,7 +16,7 @@ impl<A: Adaptor> IntoResponse for ApiError<A> {
|
|||
StatusCode::INTERNAL_SERVER_ERROR.into_response()
|
||||
}
|
||||
ApiError::NotFound => StatusCode::NOT_FOUND.into_response(),
|
||||
// ApiError::NotAuthorized => StatusCode::UNAUTHORIZED.into_response(),
|
||||
ApiError::NotAuthorized => StatusCode::UNAUTHORIZED.into_response(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -39,9 +39,10 @@ async fn main() {
|
|||
let app = Router::new()
|
||||
.route("/", get(get_root))
|
||||
.route("/stats", get(get_stats))
|
||||
.route("/event/:event_id", get(get_event))
|
||||
.route("/event", post(create_event))
|
||||
.route("/event/:event_id", get(get_event))
|
||||
.route("/event/:event_id/people", get(get_people))
|
||||
.route("/event/:event_id/people/:person_name", get(get_person))
|
||||
.with_state(shared_state);
|
||||
|
||||
let addr = SocketAddr::from(([127, 0, 0, 1], 3000));
|
||||
|
|
|
|||
|
|
@ -58,3 +58,8 @@ impl From<Person> for PersonResponse {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Deserialize)]
|
||||
pub struct PersonInput {
|
||||
pub password: Option<String>,
|
||||
}
|
||||
|
|
|
|||
87
backend/src/routes/get_person.rs
Normal file
87
backend/src/routes/get_person.rs
Normal file
|
|
@ -0,0 +1,87 @@
|
|||
use axum::{
|
||||
extract::{self, Path},
|
||||
Json,
|
||||
};
|
||||
use common::{adaptor::Adaptor, person::Person};
|
||||
|
||||
use crate::{
|
||||
errors::ApiError,
|
||||
payloads::{ApiResult, PersonInput, PersonResponse},
|
||||
State,
|
||||
};
|
||||
|
||||
pub async fn get_person<A: Adaptor>(
|
||||
extract::State(state): State<A>,
|
||||
Path((event_id, person_name)): Path<(String, String)>,
|
||||
input: Option<Json<PersonInput>>,
|
||||
) -> ApiResult<PersonResponse, A> {
|
||||
let adaptor = &state.lock().await.adaptor;
|
||||
|
||||
// Get inputted password
|
||||
let password = match input {
|
||||
Some(Json(i)) => i.password,
|
||||
None => None,
|
||||
};
|
||||
|
||||
let existing_people = adaptor
|
||||
.get_people(event_id.clone())
|
||||
.await
|
||||
.map_err(ApiError::AdaptorError)?;
|
||||
|
||||
// Event not found
|
||||
if existing_people.is_none() {
|
||||
return Err(ApiError::NotFound);
|
||||
}
|
||||
|
||||
// Check if the user already exists
|
||||
let existing_person = existing_people
|
||||
.unwrap()
|
||||
.into_iter()
|
||||
.find(|p| p.name == person_name);
|
||||
|
||||
match existing_person {
|
||||
// Login
|
||||
Some(p) => {
|
||||
// Verify password (if set)
|
||||
if verify_password(&p, password) {
|
||||
Ok(Json(p.into()))
|
||||
} else {
|
||||
Err(ApiError::NotAuthorized)
|
||||
}
|
||||
}
|
||||
// Signup
|
||||
None => {
|
||||
// Update stats
|
||||
adaptor
|
||||
.increment_stat_person_count()
|
||||
.await
|
||||
.map_err(ApiError::AdaptorError)?;
|
||||
|
||||
Ok(Json(
|
||||
adaptor
|
||||
.upsert_person(
|
||||
event_id,
|
||||
Person {
|
||||
name: person_name,
|
||||
password_hash: password
|
||||
.map(|raw| bcrypt::hash(raw, 10).unwrap_or(String::from(""))),
|
||||
created_at: chrono::offset::Utc::now(),
|
||||
availability: vec![],
|
||||
},
|
||||
)
|
||||
.await
|
||||
.map_err(ApiError::AdaptorError)?
|
||||
.into(),
|
||||
))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn verify_password(person: &Person, raw: Option<String>) -> bool {
|
||||
match &person.password_hash {
|
||||
Some(hash) => bcrypt::verify(raw.unwrap_or(String::from("")), hash).unwrap_or(false),
|
||||
// Specifically allow a user who doesn't have a password
|
||||
// set to log in with or without any password input
|
||||
None => true,
|
||||
}
|
||||
}
|
||||
|
|
@ -9,3 +9,6 @@ pub use create_event::create_event;
|
|||
|
||||
mod get_people;
|
||||
pub use get_people::get_people;
|
||||
|
||||
mod get_person;
|
||||
pub use get_person::get_person;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue