Http retry should only happen at Http Error (which are transport errors)

Fixes #939
This commit is contained in:
Cesar Rodas
2025-08-18 11:51:24 -03:00
parent d3a3c30d99
commit 29ce2e4f4d
2 changed files with 39 additions and 14 deletions

View File

@@ -290,8 +290,8 @@ pub enum Error {
#[error(transparent)]
HexError(#[from] hex::Error),
/// Http transport error
#[error("Http transport error: {0}")]
HttpError(String),
#[error("Http transport error {0:?}: {1}")]
HttpError(Option<u16>, String),
#[cfg(feature = "wallet")]
// Crate error conversions
/// Cashu Url Error

View File

@@ -64,10 +64,20 @@ impl HttpClientCore {
let response = request
.send()
.await
.map_err(|e| Error::HttpError(e.to_string()))?
.map_err(|e| {
Error::HttpError(
e.status().map(|status_code| status_code.as_u16()),
e.to_string(),
)
})?
.text()
.await
.map_err(|e| Error::HttpError(e.to_string()))?;
.map_err(|e| {
Error::HttpError(
e.status().map(|status_code| status_code.as_u16()),
e.to_string(),
)
})?;
serde_json::from_str::<R>(&response).map_err(|err| {
tracing::warn!("Http Response error: {}", err);
@@ -90,15 +100,19 @@ impl HttpClientCore {
request = request.header(auth.header_key(), auth.to_string());
}
let response = request
.send()
.await
.map_err(|e| Error::HttpError(e.to_string()))?;
let response = request.send().await.map_err(|e| {
Error::HttpError(
e.status().map(|status_code| status_code.as_u16()),
e.to_string(),
)
})?;
let response = response
.text()
.await
.map_err(|e| Error::HttpError(e.to_string()))?;
let response = response.text().await.map_err(|e| {
Error::HttpError(
e.status().map(|status_code| status_code.as_u16()),
e.to_string(),
)
})?;
serde_json::from_str::<R>(&response).map_err(|err| {
tracing::warn!("Http Response error: {}", err);
@@ -189,7 +203,12 @@ impl HttpClient {
}))
.danger_accept_invalid_certs(accept_invalid_certs) // Allow self-signed certs
.build()
.map_err(|e| Error::HttpError(e.to_string()))?;
.map_err(|e| {
Error::HttpError(
e.status().map(|status_code| status_code.as_u16()),
e.to_string(),
)
})?;
Ok(Self {
core: HttpClientCore { inner: client },
@@ -249,7 +268,13 @@ impl HttpClient {
}
match result.as_ref() {
Err(Error::Database(_) | Error::HttpError(_) | Error::Custom(_)) => {
Err(Error::HttpError(status_code, _)) => {
let status_code = status_code.to_owned().unwrap_or_default();
if status_code <= 400 && status_code >= 499 {
// 4xx errors won't be 'solved' by retrying
return result;
}
// retry request, if possible
tracing::error!("Failed http_request {:?}", result.as_ref().err());