Skip to content

compression::StreamingDecoder::new only matches a single encoding token, not a Content-Encoding list #79

Description

@proggeramlug

Problem

compression::StreamingDecoder::new(encoding: &str, ...) matches encoding as a single exact token ("gzip" | "x-gzip", "deflate", "br", "zstd", "" | "identity") and errors on anything else (protocols/turnloop-http/src/compression.rs). A Content-Encoding header is legally a comma-separated list of codings applied in order, and a server can also repeat the header across multiple lines. Neither shape is handled: the whole header value is matched as one string and fails.

Why it matters

Named by an independent review of Perry's P11 lane (the perry CLI's HTTP client, built on turnloop_http). A legal gzip, gzip — or two separate Content-Encoding header lines — failed the whole response with UND_ERR_NOT_SUPPORTED. This is a new failure mode specifically for that lane: it's the first Perry consumer to send its own Accept-Encoding, so the reqwest-based client it replaces never triggered it (it asked for no compression at all, so this path was never exercised on real traffic).

P11 worked around it on the caller side rather than in this crate — a_content_encoding_list_is_split_innermost_last pins the caller-side fix: the header value is split and each coding applied innermost-last, across every header line. compression::StreamingDecoder's own single-token match in new is unchanged.

What would fix it

Accept a list at the API boundary — an iterator of coding tokens, or split-and-chain internally — applying codings innermost-last (the last-listed encoding is the outermost, first to decode), and merging repeated Content-Encoding header lines the same way any repeated header is merged. (This is a different gap from turnloop#54, which is about StreamingDecoder::process's "needs more input" vs. "output full" ambiguity — that's after construction; this is new's single-token match.)

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions