diff options
Diffstat (limited to 'src/invite')
| -rw-r--r-- | src/invite/app.rs | 10 | ||||
| -rw-r--r-- | src/invite/routes.rs | 3 |
2 files changed, 11 insertions, 2 deletions
diff --git a/src/invite/app.rs b/src/invite/app.rs index 998b4f1..6800d72 100644 --- a/src/invite/app.rs +++ b/src/invite/app.rs @@ -4,7 +4,7 @@ use sqlx::sqlite::SqlitePool; use super::{repo::Provider as _, Id, Invite, Summary}; use crate::{ clock::DateTime, - db::NotFound as _, + db::{Duplicate as _, NotFound as _}, event::repo::Provider as _, login::{repo::Provider as _, Login, Password}, token::{repo::Provider as _, Secret}, @@ -68,7 +68,11 @@ impl<'a> Invites<'a> { // catch it. tx.invites().accept(&invite).await?; let created = tx.sequence().next(accepted_at).await?; - let login = tx.logins().create(name, &password_hash, &created).await?; + let login = tx + .logins() + .create(name, &password_hash, &created) + .await + .duplicate(|| AcceptError::DuplicateLogin(name.into()))?; let secret = tx.tokens().issue(&login, accepted_at).await?; tx.commit().await?; @@ -99,6 +103,8 @@ pub enum Error { pub enum AcceptError { #[error("invite not found: {0}")] NotFound(Id), + #[error("name in use: {0}")] + DuplicateLogin(String), #[error(transparent)] Database(#[from] sqlx::Error), #[error(transparent)] diff --git a/src/invite/routes.rs b/src/invite/routes.rs index 3384e10..977fe9b 100644 --- a/src/invite/routes.rs +++ b/src/invite/routes.rs @@ -88,6 +88,9 @@ impl IntoResponse for AcceptError { let Self(error) = self; match error { error @ app::AcceptError::NotFound(_) => NotFound(error).into_response(), + error @ app::AcceptError::DuplicateLogin(_) => { + (StatusCode::CONFLICT, error.to_string()).into_response() + } other => Internal::from(other).into_response(), } } |
