{"id":"15f4135240f712d6","repo":"seanmonstar/reqwest","slug":"http-status-client-error-code","errorCode":null,"errorMessage":"HTTP status client error ({code})","messagePattern":"HTTP status client error \\((.+?)\\)","errorType":"http","errorClass":"reqwest::Error","httpStatus":null,"severity":"error","filePath":"src/error.rs","lineNumber":373,"sourceCode":"\npub(crate) fn request<E: Into<BoxError>>(e: E) -> Error {\n    Error::new(Kind::Request, Some(e))\n}\n\npub(crate) fn dns<E: Into<BoxError>>(e: E) -> BoxError {\n    Box::new(DnsError { inner: e.into() })\n}\n\npub(crate) fn redirect<E: Into<BoxError>>(e: E, url: Url) -> Error {\n    Error::new(Kind::Redirect, Some(e)).with_url(url)\n}\n\npub(crate) fn status_code(\n    url: Url,\n    status: StatusCode,\n    #[cfg(not(all(target_arch = \"wasm32\", any(target_os = \"unknown\", target_os = \"none\"))))] reason: Option<hyper::ext::ReasonPhrase>,\n) -> Error {\n    Error::new(\n        Kind::Status(\n            status,\n            #[cfg(not(all(\n                target_arch = \"wasm32\",\n                any(target_os = \"unknown\", target_os = \"none\")\n            )))]\n            reason,\n        ),\n        None::<Error>,\n    )\n    .with_url(url)\n}\n\npub(crate) fn url_bad_scheme(url: Url) -> Error {\n    Error::new(Kind::Builder, Some(BadScheme)).with_url(url)\n}\n\npub(crate) fn url_invalid_uri(url: Url) -> Error {","sourceCodeStart":355,"sourceCodeEnd":391,"githubUrl":"https://github.com/seanmonstar/reqwest/blob/17e9bcb51c46edebfb6f5f2f5184b51dac4b3a7d/src/error.rs#L355-L391","documentation":"A `Kind::Status(4xx, ...)` error (error.rs:280-296). It is produced only by `Response::error_for_status()` (response.rs:382, 413) when the server returned a 4xx client-error status. reqwest does NOT throw this automatically — `.send()` returns the `Response` regardless of status; the error only appears if the caller explicitly turns a 4xx into an error.","triggerScenarios":"Calling `resp.error_for_status()?` (or `error_for_status_ref()` returning Err) after a 400/401/403/404/409/422/429 response.","commonSituations":"Bad request payload (400), missing/expired auth token (401/403), unknown resource (404), conflict (409), validation failure (422), rate limited (429).","solutions":["Don't call `error_for_status()` blindly; inspect `resp.status()` and the body first so you can read the API's error message.","Handle 4xx semantically (e.g. 401 → refresh token, 429 → back off via `Retry-After`).","Use `error_for_status_ref()` when you still need the response body on failure."],"exampleFix":"// before\nlet body: T = resp.error_for_status()?.json().await?; // loses API error detail\n\n// after\nlet status = resp.status();\nif status.is_client_error() {\n    let text = resp.text().await.unwrap_or_default();\n    match status.as_u16() {\n        401 => return Err(AuthError::Expired.into()),\n        429 => return Err(RateLimited.into()),\n        _ => anyhow::bail!(\"api {status}: {text}\"),\n    }\n}\nlet body: T = resp.json().await?;","handlingStrategy":"validation","validationCode":"// Inspect status before converting to an error.\nlet status = resp.status();\nif status.is_client_error() {\n    let body = resp.text().await.unwrap_or_default();\n    return Err(handle_client_error(status, body));\n}\n","typeGuard":"fn is_client_status(e: &reqwest::Error) -> bool {\n    e.status().map(|c| c.is_client_error()).unwrap_or(false)\n}\n","tryCatchPattern":"let resp = client.get(&url).send().await?;\nif resp.status().is_client_error() {\n    let text = resp.text().await.unwrap_or_default();\n    return Err(ApiError::from_status(resp.status(), text));\n}\nlet body = resp.json::<T>().await?;","preventionTips":["Don't call error_for_status() blindly; read status and body first.","Map 4xx codes to domain errors (401→refresh, 429→backoff) instead of generic failures.","Use error_for_status_ref() if you still need the body on the failure path."],"tags":["status","http","client-error","response"],"analyzedSha":"17e9bcb51c46edebfb6f5f2f5184b51dac4b3a7d","analyzedAt":"2026-08-06T01:23:05.134Z","schemaVersion":2}