seanmonstar/warp · info

valid ContentRange

Error message

valid ContentRange

What it means

In the filesystem filter, when serving a byte sub-range the code builds an HTTP `ContentRange` header via `ContentRange::bytes(start..end, len).expect("valid ContentRange")` (src/filters/fs.rs:328). The `http-range-header` crate returns an error (and warp panics) if the range is invalid: start >= end, range beyond/inconsistent with total length, or a range that cannot be represented. Given warp computes start/end/len from the actual file, this should be mathematically unreachable and is an internal invariant panic.

Solutions

  1. If you implement custom range logic, validate 0 <= start < end <= len before constructing `ContentRange::bytes(..)`
  2. Use `ContentRange::bytes(..)` with checked/clamped bounds instead of `expect` in custom filters
  3. Prefer the built-in `warp::fs::file`/`warp::fs::dir` which handle Range headers internally
  4. If hit, inspect the client's raw `Range` header for malformed values like bytes=start-end with start>end

Example fix

// before
ContentRange::bytes(start..end, len).expect("valid ContentRange"),
// after
assert!(start < end && end <= len, "invalid range {}..{} for len {}", start, end, len);
ContentRange::bytes(start..end, len).expect("valid ContentRange"),
Defensive patterns

Strategy: try-catch

Validate before calling

// before constructing a ContentRange in custom code:
fn valid_range(start: u64, end: u64, len: u64) -> bool { start < end && end <= len }

Try / catch

// warp's expect is internal; if you write custom range code:
match http_range_header::ContentRange::bytes(start..end, len) {
    Ok(cr) => resp.headers_mut().typed_insert(cr),
    Err(_) => *resp.status_mut() = StatusCode::RANGE_NOT_SATISFIABLE,
}

Prevention

When it happens

Trigger: A client sends a `Range` header and the computed sub-range (start..end) is inconsistent with the file length — theoretically only if range parsing bounds were violated. Practically unreachable through the public `warp::fs` API because warp validates ranges before slicing.

Common situations: Not normally hit by library users; could surface only if a proxy or client sends pathological Range headers that slip past validation, or with a modified/custom fs filter computing its own ranges.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of seanmonstar/warp@ff34d7213e (2026-09-09). Data as JSON: /api/errors/7f819af335a97978. Report an issue: GitHub.

Appendix: source

Thrown at src/filters/fs.rs:328

        let mut len = meta.len();
        let modified = meta.modified().ok().map(LastModified::from);

        let resp = match conditionals.check(modified) {
            Cond::NoBody(resp) => resp,
            Cond::WithBody(range) => {
                bytes_range(range, len)
                    .map(|(start, end)| {
                        let sub_len = end - start;
                        let buf_size = optimal_buf_size(&meta);
                        let stream = file_stream(file, buf_size, (start, end));
                        let body = Body::wrap_stream(stream);

                        let mut resp = Response::new(body);

                        if sub_len != len {
                            *resp.status_mut() = StatusCode::PARTIAL_CONTENT;
                            resp.headers_mut().typed_insert(
                                ContentRange::bytes(start..end, len).expect("valid ContentRange"),
                            );

                            len = sub_len;
                        }

                        let mime = mime_guess::from_path(path.as_ref()).first_or_octet_stream();

                        resp.headers_mut().typed_insert(ContentLength(len));
                        resp.headers_mut().typed_insert(ContentType::from(mime));
                        resp.headers_mut().typed_insert(AcceptRanges::bytes());

                        if let Some(last_modified) = modified {
                            resp.headers_mut().typed_insert(last_modified);
                        }

                        resp
                    })
                    .unwrap_or_else(|BadRange| {

View on GitHub (pinned to ff34d7213e)