nytimes / gziphandler

Go middleware to gzip HTTP responses
https://godoc.org/github.com/NYTimes/gziphandler
Apache License 2.0
868 stars 129 forks source link

net::ERR_CONTENT_LENGTH_MISMATCH #17

Closed wayneashleyberry closed 8 years ago

wayneashleyberry commented 8 years ago

Hey, if I take the example in the readme and try to use it with a static directory server I get a net::ERR_CONTENT_LENGTH_MISMATCH error in the browser. Here's the example with the test code I've added:

package main

import (
    "io"
    "net/http"
    "os"

    "github.com/nytimes/gziphandler"
)

func main() {
    withoutGz := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        w.Header().Set("Content-Type", "text/plain")
        io.WriteString(w, "Hello, World")
    })

    withGz := gziphandler.GzipHandler(withoutGz)

    dirWithoutGz := http.FileServer(http.Dir("./"))
    dirWithGz := gziphandler.GzipHandler(dirWithoutGz)

    http.Handle("/", withGz)
    http.Handle("/test.jpg", dirWithGz)
    http.ListenAndServe(":"+os.Getenv("PORT"), nil)
}

If you use the dirWithoutGz handler then the image returns just fine, but the dirWithGz handler errors. Am I misunderstanding something?

Here's some debug information if this helps:

$GOPATH/src/github.com/nytimes/gziphandler master
❯ git rev-parse HEAD
44668d75e46f05932cf7c1c7a375d0765b324a0b
❯ go version
go version go1.7.1 darwin/amd64
tamasd commented 8 years ago

I have a test case that started failing in the last few days. There is a similar one that succeeds. The one that fails serves an html file (with http.ServeFile()), and the one that succeeds serves a binary file the same way. The code is exactly the same, only the file name is different.

In case of the html file, the headers are:

HTTP/1.1 200 OK
Accept-Ranges: bytes
Content-Type: text/html; charset=utf-8
Date: Sun, 18 Sep 2016 17:52:39 GMT
Last-Modified: Sun, 14 Jun 2015 14:24:51 GMT
Set-Cookie: _SESSION=; Path=/; Expires=Mon, 18 Sep 2017 17:52:39 GMT; HttpOnly
Vary: Accept-Encoding

But in case of the binary file, the headers are different:

HTTP/1.1 200 OK
Transfer-Encoding: chunked
Content-Type: application/octet-stream
Date: Sun, 18 Sep 2016 17:52:39 GMT
Set-Cookie: _SESSION=; Path=/; Expires=Mon, 18 Sep 2017 17:52:39 GMT; HttpOnly
Vary: Accept-Encoding

I use http.Client in both cases to retrive the results. In the failing case, ioutil.ReadAll() returns an io.ErrUnexpectedEOF error, but the returned data matches exactly the data on the disk. If I disable the gzip encoding in the failing case, by sending Accept-Encoding: identity, the test succeeds. In both cases, the response's Uncompressed field is true.

tamasd commented 8 years ago

I did a bisect. My tests are green with 44afc59. The next commit d3d7d67 makes a lot of my tests fail, and then at cdd181b I can reproduce the exact same failure.

wayneashleyberry commented 8 years ago

Thanks for the fix @jprobinson 🎉