Skip to content

fix(engine): treat Content-Encoding: none as no-op, not unsupported - #233

Merged
zerx-lab merged 1 commit into
mainfrom
farm/51af1f5c/fix-content-encoding-none
Jul 31, 2026
Merged

fix(engine): treat Content-Encoding: none as no-op, not unsupported#233
zerx-lab merged 1 commit into
mainfrom
farm/51af1f5c/fix-content-encoding-none

Conversation

@ZerxLabBot

Copy link
Copy Markdown
Collaborator

Repro

A server responds with the header Content-Encoding: none (a non-standard but self-explanatory token some servers/proxies send to mean "no compression applied", instead of omitting the header or sending identity). Any download attempt against such a server — single-stream or segmented — fails with: server applied an unsupported or multi-layered response compression scheme 'none'; cannot decode the body — refusing to write raw bytes to disk. This exactly matches the reporter's client log in #232.

Cause

unsupported_content_encoding() in native/engine/src/downloader.rs:641-667 only whitelists identity and "" as no-op tokens; any other token (including none) is treated as an unknown/undecodable encoding layer and returned as Some(...). The caller at downloader.rs:3623 (single-stream path) and segment_coordinator.rs:4752 (segmented path) both turn that into a hard error. This failure is deliberately excluded from the retriable-error set (see the comment above the call site), so it can never self-recover — every future attempt against that server fails identically. detect_content_encoding() already treated unknown tokens (including none) as a no-op (falls through to None), so the two gates disagreed with each other.

Fix

  • Add "none" to the no-op arm of unsupported_content_encoding() alongside "identity" and "", with a comment explaining why (BUG-HTTP-NONE-ENCODING-FALSE-POSITIVE).
  • Both call sites (single-stream downloader.rs and segmented segment_coordinator.rs) share this function, so the fix applies to both download paths without further changes.
  • Added unit tests: none/identity/gzip are accepted as no-op; unknown tokens (compress) and multi-layer encodings (gzip, gzip) still correctly rejected — locking in both the fix and the existing protection this function provides.

Verification

Not built or tested in this environment (no Rust/Flutter toolchain available here). Verified statically:

  • Traced unsupported_content_encoding("none") through the match arms: previously fell into the other arm (has_unknown = true) producing the exact reported error string; now matches the "identity" | "none" | "" no-op arm and returns None.
  • Confirmed detect_content_encoding requires no change — it already maps unknown tokens (including none) to None, so the body is correctly treated as already-uncompressed and written as-is.
  • Confirmed brace/arm structure of the edited match block is balanced (7 {/7 } in the function).
  • Added 5 new #[test] cases mirroring the existing detect_content_encoding_* test style in the same module; not executed (no cargo).

Please run before merge:

  • cargo check -p fluxdown_engine --lib
  • cargo nextest run -p fluxdown_engine unsupported_content_encoding
  • cargo nextest run -p fluxdown_engine detect_content_encoding

Known unaffected/not covered: fluxdown_api, hub, server, Dart/web clients — this is purely an engine-internal HTTP response classification fix, no wire contract or DB schema change.

Fixes #232

Some servers/proxies send the non-standard but self-explanatory
Content-Encoding: none to state that no compression was applied,
instead of omitting the header or sending identity. unsupported_content_encoding()
only whitelisted "identity" and "" as no-op tokens, so "none" fell
into the unknown-encoding branch and every download from such a
server was permanently refused (this failure is excluded from the
retriable set by design, so retries could never recover it).

Add "none" to the no-op whitelist in
native/engine/src/downloader.rs::unsupported_content_encoding, used
by both the single-stream (downloader.rs) and segmented
(segment_coordinator.rs) download paths. detect_content_encoding
already treated "none" as no-op (unknown tokens fall through to
None there), so this fix aligns the two gates.

Fixes #232
@zerx-lab
zerx-lab merged commit 6885102 into main Jul 31, 2026
@zerx-lab
zerx-lab deleted the farm/51af1f5c/fix-content-encoding-none branch July 31, 2026 00:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

🐛 [App Feedback] 無法下載

2 participants