GitoxideLabs/gitoxide · error
Received HTTP status
Error message
Received HTTP status {} What it means
The HTTP remote (reqwest-based) received a non-success HTTP status from the server and converts it into an `io::Error` whose message carries the status string, with an ErrorKind mapped by status class (PermissionDenied for 401/403-style auth failures, ConnectionAborted for 5xx, Other otherwise). This indicates the server rejected the request.
Solutions
- Check the HTTP status in the message and fix auth: update tokens/credentials via the configured credential helper
- Verify the repository URL exists and the account has access
- Retry on 5xx/429 with backoff; check the provider's status page for outages
Example fix
// before (403)
let mut conn = gix::connect(url, gix::protocol::transport::Protocol::Http)?;
// after: embed credentials
let url = format!("https://token@github.com/user/repo.git");
let mut conn = gix::connect(url, gix::protocol::transport::Protocol::Http)?; Defensive patterns
Strategy: retry
Validate before calling
fn check_url(url: &str) -> Result<(), String> {
let u = gix::url::parse(url.into())?;
if u.scheme != gix::url::Scheme::Https { return Err("expected https".into()); }
Ok(())
} Try / catch
match remote.fetch(...) {
Err(e) if e.to_string().contains("Received HTTP status") => {
if e.to_string().contains("403") || e.to_string().contains("401") {
// refresh credentials via credential helper, then retry once
} else {
// 5xx/429: retry with exponential backoff
}
}
other => other?,
} Prevention
- Keep credentials/tokens fresh and scoped to the repo
- Check provider status pages before assuming a code bug on 5xx
- Respect Retry-After headers on 429 rate limits
- Validate repository URLs and permissions up front
When it happens
Trigger: Any git HTTP operation (fetch/clone/push over the reqwest transport) where the server responds with an error status — 401/403 auth failures, 404 repo not found, 5xx server errors, rate limiting (429).
Common situations: Wrong or expired credentials/tokens; private repository with insufficient access; GitHub/GitLab outages or rate limits; proxy interference returning error pages.
Understand the failure class
Background: "API error: {status}" and "HTTP 401/403/404/429/5xx" errors: non-2xx HTTP responses explained — this error's family across 27 libraries.
Related errors
- Tried to use as tree, but was
- Tried to use as commit, but was
- Tried to use as tag, but was
- invalid mode change: can't flip executable bit of
- visit_non_tree() called us
AI-assisted analysis of GitoxideLabs/gitoxide@e73179060b (2026-09-08).
Data as JSON: /api/errors/08decacf3f8034ed.
Report an issue: GitHub.
Appendix: source
Thrown at gix-transport/src/client/blocking_io/http/reqwest/remote.rs:197
Err(err) => {
// `error_for_status()` preserves the final URL for HTTP error responses. Capture it here so
// authentication retries after redirected 401 responses use the redirected base URL.
if let Some(actual_url) = err.url().map(reqwest::Url::as_str)
&& actual_url != effective_url
{
let new_base_url = redirect::base_url(actual_url, &base_url, url.clone())?;
*redirected_base_url_shared.lock() = Some(new_base_url);
}
let err = match err.status() {
Some(status) => {
let kind = if status == reqwest::StatusCode::UNAUTHORIZED {
std::io::ErrorKind::PermissionDenied
} else if status.is_server_error() {
std::io::ErrorKind::ConnectionAborted
} else {
std::io::ErrorKind::Other
};
std::io::Error::new(kind, format!("Received HTTP status {}", status.as_str()))
}
// Preserve the `reqwest::Error` as the source so the underlying cause -- e.g. a
// connection or TLS failure -- isn't lost. It was previously stringified, which
// dead-ended `source()` and hid the real reason a request failed. See #2140.
None => std::io::Error::other(err),
};
headers_tx.channel.send(Err(err)).ok();
continue;
}
};
let actual_url = res.url().as_str();
if actual_url != effective_url.as_str() {
let new_base_url = redirect::base_url(actual_url, &base_url, url)?;
*redirected_base_url_shared.lock() = Some(new_base_url);
}
let send_headers = {View on GitHub (pinned to e73179060b)