diff --git a/src/main.rs b/src/main.rs index 6503e39..9a747fc 100644 --- a/src/main.rs +++ b/src/main.rs @@ -63,6 +63,17 @@ enum Error { UnknownError(String), } +impl From for Error { + fn from(value: object_store::Error) -> Self { + match value { + object_store::Error::NotFound { path, source: _ } => { + Self::NotFound(format!("object not found at {}", path)) + } + err => Error::UnknownError(err.to_string()), + } + } +} + #[rocket::get("/")] async fn index_root(state: &State) -> Result { index(None, state).await @@ -81,27 +92,24 @@ async fn index(path: Option, state: &State) -> Result, state: &State) -> Result Result { + log::debug!("checking existence of S3 object at {}", s3_path); match settings.s3_bucket.head(s3_path).await { Ok(_metadata) => Ok(true), Err(object_store::Error::NotFound { path: _, source: _ }) => Ok(false), @@ -123,10 +132,7 @@ async fn serve_object(s3_path: &ObjectStorePath, settings: &Settings) -> Result< .s3_bucket .get(&s3_path) .await - .map_err(|e| match e { - object_store::Error::NotFound { path: _, source: _ } => Error::NotFound(e.to_string()), - _ => Error::UnknownError(e.to_string()), - })? + .map_err(Error::from)? .into_stream(); let s3_path = s3_path.clone(); @@ -161,12 +167,7 @@ async fn file_view( .s3_bucket .list_with_delimiter(s3_folder_path.as_ref()) .await - .map_err(|err| match err { - object_store::Error::NotFound { path: _, source: _ } => { - Error::NotFound("object not found".into()) - } - err => Error::UnknownError(err.to_string()), - })?; + .map_err(Error::from)?; let folders = s3_objects.common_prefixes.into_iter().map(|dir| { let dirname = dir.parts().last().unwrap(); diff --git a/src/settings.rs b/src/settings.rs index 26b9d27..9f7e98d 100644 --- a/src/settings.rs +++ b/src/settings.rs @@ -2,9 +2,10 @@ // SPDX-License-Identifier: EUPL-1.2 use { - object_store::{ObjectStore, aws}, + object_store::{BackoffConfig, ObjectStore, RetryConfig, aws}, rocket::serde::Deserialize, serde::de::Error, + std::time::Duration, }; #[derive(Deserialize)] @@ -48,6 +49,11 @@ impl TryInto> for S3Config { .with_secret_access_key(self.secret_access_key) .with_virtual_hosted_style_request(!self.path_style) .with_allow_http(true) + .with_retry(RetryConfig { + max_retries: 1, + backoff: BackoffConfig::default(), + retry_timeout: Duration::from_millis(500), + }) .build()?; log::info!(