泽西岛的 GZip 编码

GZip encoding in Jersey

我正在 Jersey 2 中编写 RESTful 网络服务。我想支持响应的 Gzip 编码。在 this answer 之后,我在 ResourceConfig class.

中启用了 org.glassfish.jersey.server.filter.EncodingFilter
public class MyWebService extends ResourceConfig {
    public MyWebService() {
        register(EncodingFilter.class);
        register(GZipEncoder.class);
        register(DeflateEncoder.class);
    }
}

在我的资源 class 上,我返回 javax.ws.rs.core.Response object。

@GET
@Path("api/configs") 
public Response listConfigs() throws Exception {
    List<UserConfig> configs = configService.getAll();
    return Response.ok().entity(configs).build();
}

现在,当我点击 api 时,我得到了一个响应,但是响应 header 不包含 Content-Encoding header,而是包含 Transfer-Encoding: chunked.

要求:

> GET /api/configs HTTP/1.1
> Accept-Encoding: gzip

回复:

> HTTP/1.1 200 
> Transfer-Encoding: chunked
* Received 14.8 KB chunk
* Received 504 B chunk
* Received 15.2 KB chunk
* Received 506 B chunk
* Received 15.1 KB chunk
* Received 514 B chunk

回复中没有Content-Encoding: gzipheader,也没有Content-Lengthheader.

我在 Tomcat 9 上使用 Jersey 2.27

我还缺少任何其他配置吗?我如何获得这两个 headers 并获得 gzip 压缩的响应而不是接收分块响应?

编辑:我注意到当我发送大文件(> 1000 KB)时,我同时收到 Content-Encoding: gzipTransfer-Encoding: chunked headers.

使用Transfer-Encoding还是Content-Length完全由容器决定。这取决于允许的缓冲区大小。

如果容器必须设置Content-Length头,它必须事先知道压缩响应的长度,因此,容器必须在内存中缓冲整个响应。

对于 Jersey,内容长度缓冲区大小由 ServerProperties.OUTBOUND_CONTENT_LENGTH_BUFFER 定义。默认情况下,这是 8192 bytes.

您可以通过 MyWebService class:

轻松增加此值
public class MyWebService extends ResourceConfig {
    public MyWebService() {
        register(EncodingFilter.class);
        register(GZipEncoder.class);
        register(DeflateEncoder.class);

        ...

        property(ServerProperties.OUTBOUND_CONTENT_LENGTH_BUFFER, 32768);

    }
}

希望这对您有所帮助。