From 922988e05212991b476a845c9fb543be80080226 Mon Sep 17 00:00:00 2001 From: vibhor-aggr Date: Thu, 11 Jun 2026 19:23:23 +0530 Subject: [PATCH 1/3] Skip compression for partial content responses --- index.js | 6 ++++++ test/compression.js | 19 +++++++++++++++++++ 2 files changed, 25 insertions(+) diff --git a/index.js b/index.js index c0638e08..05d66328 100644 --- a/index.js +++ b/index.js @@ -171,6 +171,12 @@ function compression (options) { return } + // response is partial content + if (res.statusCode === 206) { + nocompress('partial content') + return + } + // vary vary(res, 'Accept-Encoding') diff --git a/test/compression.js b/test/compression.js index 8107def0..77de019d 100644 --- a/test/compression.js +++ b/test/compression.js @@ -67,6 +67,25 @@ describe('compression()', function () { .expect(200, 'hello, world', done) }) + it('should skip partial content responses', function (done) { + var server = createServer({ threshold: 0 }, function (req, res) { + res.statusCode = 206 + res.setHeader('Content-Type', 'text/plain') + res.setHeader('Content-Range', 'bytes 0-4/12') + res.setHeader('Content-Length', '5') + res.end('hello') + }) + + request(server) + .get('/') + .set('Accept-Encoding', 'gzip') + .set('Range', 'bytes=0-4') + .expect(shouldNotHaveHeader('Content-Encoding')) + .expect('Content-Range', 'bytes 0-4/12') + .expect('Content-Length', '5') + .expect(206, 'hello', done) + }) + it('should set Vary', function (done) { var server = createServer({ threshold: 0 }, function (req, res) { res.setHeader('Content-Type', 'text/plain') From 203861ecac431f328a193b947dabc1816610d7ae Mon Sep 17 00:00:00 2001 From: Ulises Gascon Date: Wed, 9 Sep 2026 11:45:28 +0200 Subject: [PATCH 2/3] test: cover 206 partial content skip --- test/compression.js | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/test/compression.js b/test/compression.js index 77de019d..6a39df99 100644 --- a/test/compression.js +++ b/test/compression.js @@ -79,13 +79,31 @@ describe('compression()', function () { request(server) .get('/') .set('Accept-Encoding', 'gzip') - .set('Range', 'bytes=0-4') .expect(shouldNotHaveHeader('Content-Encoding')) + .expect(shouldNotHaveHeader('Vary')) .expect('Content-Range', 'bytes 0-4/12') .expect('Content-Length', '5') .expect(206, 'hello', done) }) + it('should skip partial content responses set via writeHead', function (done) { + var server = createServer({ threshold: 0 }, function (req, res) { + res.writeHead(206, { + 'Content-Type': 'text/plain', + 'Content-Range': 'bytes 0-4/12', + 'Content-Length': '5' + }) + res.end('hello') + }) + + request(server) + .get('/') + .set('Accept-Encoding', 'gzip') + .expect(shouldNotHaveHeader('Content-Encoding')) + .expect('Content-Range', 'bytes 0-4/12') + .expect(206, 'hello', done) + }) + it('should set Vary', function (done) { var server = createServer({ threshold: 0 }, function (req, res) { res.setHeader('Content-Type', 'text/plain') From 63d9224ff7d7b052148344eee150b2d85f3cccb1 Mon Sep 17 00:00:00 2001 From: Ulises Gascon Date: Wed, 9 Sep 2026 11:45:33 +0200 Subject: [PATCH 3/3] docs: note 206 partial content skip --- HISTORY.md | 5 +++++ README.md | 4 +++- 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index 0678bf2a..5b90a7bc 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,3 +1,8 @@ +unreleased +========== + + * Skip compression for `206 Partial Content` responses + 1.8.1 / 2025-07-17 ========== diff --git a/README.md b/README.md index 98c5f38c..39610a29 100644 --- a/README.md +++ b/README.md @@ -41,7 +41,9 @@ the middleware, based on the given `options`. This middleware will never compress responses that include a `Cache-Control` header with the [`no-transform` directive](https://tools.ietf.org/html/rfc7234#section-5.2.2.4), -as compressing will transform the body. +as compressing will transform the body. It will also never compress +[`206 Partial Content`](https://www.rfc-editor.org/rfc/rfc9110#section-15.3.7) +responses, as the `Content-Range` header describes the uncompressed body. #### Options