zed-industries/zed · error

Baseten API returned {status}: {body}

Error message

Baseten API returned {status}: {body}

What it means

Raised in predict.rs when the HTTP call to the Baseten model-serving API completes with a non-2xx status. The message embeds both the status code and the raw response body, which usually contains Baseten's error detail (auth failure, cold-start/gateway error, invalid model id, or an application-level exception raised inside the deployed model). Parsing of the body as RawCompletionResponse happens only after this check, so a bail here means the gateway answered with an error page, not a completion.

Source

Thrown at crates/edit_prediction_cli/src/predict.rs:675

    let request = http_client::Request::builder()
        .method(Method::POST)
        .uri(&url)
        .header("Content-Type", "application/json")
        .header("Authorization", format!("Api-Key {api_key}"))
        .body(AsyncBody::from(body_bytes))?;

    let mut response = http_client.send(request).await?;
    let status = response.status();

    let mut body = String::new();
    response
        .body_mut()
        .read_to_string(&mut body)
        .await
        .context("Failed to read Baseten response body")?;

    if !status.is_success() {
        anyhow::bail!("Baseten API returned {status}: {body}");
    }

    let completion: RawCompletionResponse =
        serde_json::from_str(&body).context("Failed to parse Baseten response")?;

    let actual_output = completion
        .choices
        .into_iter()
        .next()
        .map(|choice| choice.text)
        .unwrap_or_default();

    let actual_output = format!("{prefill}{actual_output}");

    let (actual_patch, actual_cursor) =
        parse_prediction_output(example, &actual_output, PredictionProvider::Zeta2(format))?;

    let prediction = ExamplePrediction {

View on GitHub (pinned to f4178619ac)

Solutions

  1. Read the embedded status and body: 401/403 -> fix the API key, 404 -> fix the model/deployment id, 429 -> back off, 5xx -> retry shortly
  2. Verify the deployment is live and healthy in the Baseten dashboard before re-running
  3. For transient 5xx/429 wrap the run in a retry with backoff; predictions are per-example so a re-run resumes from existing results

Example fix

// before: single shot, whole run dies on one 502
let response = client.send(request).await?;

// after: retry transient statuses
for attempt in 0..3 {
    let response = client.send(request.clone()).await?;
    if response.status().is_success() || response.status().as_u16() < 500 { break; }
    tokio::time::sleep(Duration::from_secs(2u64.pow(attempt))).await;
}
Defensive patterns

Strategy: retry

Try / catch

for attempt in 0..4 {
    match send_baseten_request(&client, &request).await {
        Ok(resp) => return Ok(resp),
        Err(e) if attempt < 3 && e.to_string().contains("Baseten API returned 5") => {
            tokio::time::sleep(Duration::from_secs(2u64.pow(attempt as u32))).await;
        }
        Err(e) if e.to_string().contains("Baseten API returned 40") => {
            anyhow::bail!("Baseten auth/model id problem, do not retry: {e:#}");
        }
        Err(e) => return Err(e),
    }
}
unreachable!()

Prevention

When it happens

Trigger: Using the baseten provider for prediction: expired/invalid BASSETEN_API_KEY -> 401/403; wrong model deployment id -> 404; model crashed or timed out inside the deployment -> 500 with a traceback in {body}; rate limiting -> 429.

Common situations: Rotated API keys not updated in the environment; deployment id from a different Baseten project or a redeployed model; intermittent 502/504 while the deployment cold-starts under load.

Related errors


AI-assisted analysis of zed-industries/zed@f4178619ac (2026-08-20). Data as JSON: /api/errors/491652ae2f262ee3. Report an issue: GitHub.