diff --git a/src/login/static_provider.rs b/src/login/static_provider.rs index cc6ffb6..a95ab24 100644 --- a/src/login/static_provider.rs +++ b/src/login/static_provider.rs @@ -29,12 +29,15 @@ impl StaticLoginProvider { #[async_trait] impl LoginProvider for StaticLoginProvider { async fn login(&self, username: &str, password: &str) -> Result { + tracing::debug!(user=%username, "login"); match self.users.get(username) { None => bail!("User {} does not exist", username), Some(u) => { + tracing::debug!(user=%username, "verify password"); if !verify_password(password, &u.password)? { bail!("Wrong password"); } + tracing::debug!(user=%username, "fetch bucket"); let bucket = u .bucket .clone() @@ -43,6 +46,7 @@ impl LoginProvider for StaticLoginProvider { "No bucket configured and no default bucket specieid" ))?; + tracing::debug!(user=%username, "fetch configuration"); let storage = StorageCredentials { k2v_region: self.k2v_region.clone(), s3_region: self.s3_region.clone(), @@ -51,6 +55,7 @@ impl LoginProvider for StaticLoginProvider { bucket, }; + tracing::debug!(user=%username, "fetch keys"); let keys = match (&u.master_key, &u.secret_key) { (Some(m), Some(s)) => { let master_key = Key::from_slice(&base64::decode(m)?) @@ -69,6 +74,7 @@ impl LoginProvider for StaticLoginProvider { _ => bail!("Either both master and secret key or none of them must be specified for user"), }; + tracing::debug!(user=%username, "logged"); Ok(Credentials { storage, keys }) } } diff --git a/src/server.rs b/src/server.rs index ba89111..432f597 100644 --- a/src/server.rs +++ b/src/server.rs @@ -26,8 +26,8 @@ impl Connection { } impl Service for Connection { type Response = Response; - type Error = anyhow::Error; - type Future = BoxFuture<'static, Result>; + type Error = boitalettres::errors::Error; + type Future = BoxFuture<'static, Result>; fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll> { Poll::Ready(Ok(())) @@ -35,6 +35,7 @@ impl Service for Connection { fn call(&mut self, req: Request) -> Self::Future { tracing::debug!("Got request: {:#?}", req); + let mailstore = self.mailstore.clone(); Box::pin(async move { use imap_codec::types::{ command::CommandBody, @@ -51,9 +52,22 @@ impl Service for Connection { .with_body(body) } CommandBody::Login { - username: _, - password: _, - } => Response::ok("Logged in")?, + username, + password, + } => { + let (u, p) = match (String::try_from(username), String::try_from(password)) { + (Ok(u), Ok(p)) => (u, p), + _ => { return Response::bad("Invalid characters") } + }; + + tracing::debug!(user = %u, "command.login"); + let creds = match mailstore.login_provider.login(&u, &p).await { + Err(_) => { return Response::no("[AUTHENTICATIONFAILED] Authentication failed.") } + Ok(c) => c, + }; + + Response::ok("Logged in")? + } _ => Response::bad("Error in IMAP command received by server.")?, };