{"record":{"id":"a390d6f86b4ebf28","repo":"zeroclaw-labs/zeroclaw","slug":"failed-to-build-reqwest-client","errorCode":null,"errorMessage":"failed to build reqwest client","messagePattern":"failed to build reqwest client","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"critical","filePath":"crates/zeroclaw-runtime/src/skillforge/scout.rs","lineNumber":92,"sourceCode":"        headers.insert(\n            reqwest::header::ACCEPT,\n            \"application/vnd.github+json\".parse().expect(\"valid header\"),\n        );\n        headers.insert(\n            reqwest::header::USER_AGENT,\n            \"ZeroClaw-SkillForge/0.1\".parse().expect(\"valid header\"),\n        );\n        if let Some(ref t) = token\n            && let Ok(val) = format!(\"Bearer {t}\").parse()\n        {\n            headers.insert(reqwest::header::AUTHORIZATION, val);\n        }\n\n        let client = reqwest::Client::builder()\n            .default_headers(headers)\n            .timeout(Duration::from_secs(30))\n            .build()\n            .expect(\"failed to build reqwest client\");\n\n        Self {\n            client,\n            queries: vec![\"zeroclaw skill\".into(), \"ai agent skill\".into()],\n        }\n    }\n\n    /// Parse the GitHub search/repositories JSON response.\n    fn parse_items(body: &serde_json::Value) -> Vec<ScoutResult> {\n        let items = match body.get(\"items\").and_then(|v| v.as_array()) {\n            Some(arr) => arr,\n            None => return vec![],\n        };\n\n        items\n            .iter()\n            .filter_map(|item| {\n                let name = item.get(\"name\")?.as_str()?.to_string();","sourceCodeStart":74,"sourceCodeEnd":110,"githubUrl":"https://github.com/zeroclaw-labs/zeroclaw/blob/88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc/crates/zeroclaw-runtime/src/skillforge/scout.rs#L74-L110","documentation":"The SkillForge scout constructor builds a long-lived HTTP client with default headers and a 30-second timeout. `reqwest::Client::builder().build()` returns Err when the TLS backend cannot initialize (broken OpenSSL install, missing CA store, rustls/native-tls feature mismatch); `.expect()` turns that into a process abort at Scout::new time.","triggerScenarios":"Calling `Scout::new(...)` in a container without CA certificates, after a dependency upgrade changed the reqwest TLS backend, or on a host where the native TLS library cannot load.","commonSituations":"Minimal Docker images (alpine/distroless) missing ca-certificates; `cargo update` flipping between native-tls and rustls; air-gapped hosts with a broken OpenSSL; CI images without cert bundles.","solutions":["Install or refresh certificates and the TLS library in the runtime image (e.g. `apt-get install -y ca-certificates`) or pin reqwest to the rustls-tls feature in Cargo.toml","Construct the scout once at process startup so a TLS failure surfaces as a clean startup error rather than a mid-run panic","Change `Scout::new` to return `Result<Self>` and propagate the build error with `?` instead of `.expect()`"],"exampleFix":"// before\nlet client = reqwest::Client::builder()\n    .default_headers(headers)\n    .timeout(Duration::from_secs(30))\n    .build()\n    .expect(\"failed to build reqwest client\");\n\n// after\nlet client = reqwest::Client::builder()\n    .default_headers(headers)\n    .timeout(Duration::from_secs(30))\n    .build()?; // Scout::new returns anyhow::Result<Self>","handlingStrategy":"validation","validationCode":"fn assert_http_stack_ready() -> anyhow::Result<()> {\n    reqwest::Client::builder()\n        .timeout(std::time::Duration::from_secs(30))\n        .build()\n        .map_err(|e| anyhow::anyhow!(\"HTTP stack unusable: {e}\"))?;\n    Ok(())\n}\n// call once at process startup, before any scout is constructed","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Install ca-certificates in minimal container images and pin the reqwest TLS backend (rustls) to avoid OpenSSL drift","Construct long-lived HTTP clients once at startup where a failure is a visible, actionable error"],"tags":["rust","reqwest","tls","panic","http-client","startup"],"backgroundTag":"http-client-init-failed","analyzedSha":"88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc","analyzedAt":"2026-08-23T01:07:41.857Z","schemaVersion":2},"datasetVersion":"2026-08-23T08:06:27.607Z"}