Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Gzip compression not working in my project with Spring boot 1.5.10.RELEASE

I am using Spring Boot 1.5.10.RELEASE version. Gzip compress not working.

http://localhost:9000 --> http://localhost:8080/api/..

Angularjs & rest api on different Port. Enabled CrossOrigin to accept request from angularjs ui.

Using embedded tomcat server to deploy spring boot application. Not using http2 property i.e. server.http2.enabled=true

Angualrjs calls rest api. Following is $http service

$http({
  method: method,
  url: url,
  params: params,
  data: body,
  headers: {
    Authorization: token,
    "Content-type": 'application/json'
  }
});

Rest api response size Approx 25 MB so I want to compress response.

I have added well known property in application.properties to apply gzip compression. Spring boot 1.5.10 Supported properties

# Enable response compression
server.compression.enabled=true

# The comma-separated list of mime types that should be compressed
server.compression.mime-types=text/html,text/xml,text/plain,text/css,text/javascript,application/javascript,application/json

# Compress the response only if the response size is at least 1KB
server.compression.min-response-size=1024

I have observed network tab and no observed Content-Encoding: gzip in response header.

Request

Request URL: http://localhost:9081/employee
Request Method: GET
Status Code: 200 
Remote Address: [::1]:9081
Referrer Policy: no-referrer-when-downgrade

Response Header

Access-Control-Allow-Credentials: true
Access-Control-Allow-Origin: http://localhost:7000
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Content-Type: application/json;charset=UTF-8
Date: Sun, 28 Jun 2020 18:15:17 GMT
Expires: 0
Pragma: no-cache
Set-Cookie: JSESSIONID=6E7C07874D0329E18A0C07E5E303F005; Path=/; HttpOnly
Transfer-Encoding: chunked
Vary: Origin
X-Application-Context: application
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
X-XSS-Protection: 1; mode=block

Request Header

Accept: */*
Accept-Encoding: gzip, deflate, br
Accept-Language: en-US,en;q=0.9
Authorization: Bearer eyJhbGciOiJIUzINiJ9.eyJyb2xlIjiU0VDVE9SSEVBRCIsImxldmVsRG93biI6IkVENzA0MTI7TU04MzcyNDtKTDgzNTwO0RNNDAwNzE7Skc3MzA0NjtFQzM0NjEzO05OMTY5Nzk7QUs2MDYzNztTVDE4NTg4O0FTMjczNTE7Q0I4MTg3OTtWQTc4MTk5O0NNOTM3MDA7QVkyMzYzNztKUzcwMDY4O0NCMTc2NzE7TksyMTU2MDtMUzg4OTg0O0FQNTg3MDg7VFcyjk0NTtKSzI1Nzc3O01TNDk5MjE7SkI4OTcyOTtNSDAyMTI3O01CMTUwODk7SU0xMjgwODtNQzcxOTc2O1JSMjAzMDI7TFM1ODk4MiIsImxldmVsVXAiOm51bGwsImRlbGVnYXRlZCI6bnVsbCwic29lSWQiOiJTUjQ0MTg1I0.*************
Cache-Control: no-cache
Connection: keep-alive
Content-type: application/json
Host: localhost:9081
Origin: http://localhost:7000
Pragma: no-cache
Referer: http://localhost:7000/build/standalone.html
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-site
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/83.0.4103.97 Safari/537.36

I am not getting following expected headers in response header

Content-Encoding: gzip
Vary: Accept-Encoding

Any changes require at client /server side ?

---[Edit-1] ------------- Tried gzip in individual project which worked but not worked in my project.

Following is response header when invoke rest api from browser

Content-Encoding: gzip
Content-Type: application/json;charset=UTF-8
Date: Sun, 28 Jun 2020 18:12:29 GMT
Transfer-Encoding: chunked
Vary: Accept-Encoding

-----[Edit-2]-----Ziplet----

Using ziplet dependency I am able to compress response, but I want to use spring boot gzip compression.

Response header - when used Ziplet

Access-Control-Allow-Credentials: true
Access-Control-Allow-Origin: http://localhost:7000
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Content-Encoding: gzip
Content-Type: application/json;charset=UTF-8
Date: Mon, 06 Jul 2020 18:31:07 GMT
Expires: 0
Pragma: no-cache
Set-Cookie: JSESSIONID=8465D2E81A1A9CE146255B6C545FBE30; Path=/; HttpOnly
Transfer-Encoding: chunked
Vary: Accept-Encoding
Vary: Origin
X-Application-Context: application
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
X-XSS-Protection: 1; mode=block

When used ziplet - I can see CompressingFilter : CompressingFilter has initialized

When using Spring boot gzip compression not observed anything where I can assume gzip compression enabled.

Any property to debug spring boot gzip compression with embeded tomcat ? like logging.level.org.eclipse.jetty.server.handler.gzip=TRACE

How can i verify server.compression.enabled ?

Any changes require at client /server side in my project?

Thanks in advance.

like image 688
StackOverFlow Avatar asked Jun 28 '20 18:06

StackOverFlow


People also ask

How do you check gzip compression is enabled or not?

Double click on the file and select headers. Under 'Response headers' you are looking for the 'Connection-Encoding' field, it will say gzip if it is enabled.

How do I enable gzip compression?

It's also one of the two recommended web servers by WordPress. To enable GZIP compression on Apache servers, you need to use its mod_filter and mod_deflate modules and configure them properly with the right directives. They will direct Apache to compress server output before sending it to clients over the network.

How do I enable gzip in Apache?

To turn on Gzip compression, simply add on to the gzip directive in the main Nginx configuration file. $ sudo nano /etc/nginx/nginx. conf gzip on; Add file types to compress.

Is gzip enabled by default?

Gzip Compression is Enabled by Default.


1 Answers

As your question, you are using Spring Boot 1.5.10.RELEASE.

For that version of the framework, the class TomcatEmbeddedServletContainerFactory is responsible for starting the embedded Tomcat container.

The source code of that class and version can be found here:

https://github.com/spring-projects/spring-boot/blob/v1.5.10.RELEASE/spring-boot/src/main/java/org/springframework/boot/context/embedded/tomcat/TomcatEmbeddedServletContainerFactory.java

In this class, you can find the method customizeCompression:

private void customizeCompression(Connector connector) {
  ProtocolHandler handler = connector.getProtocolHandler();
  if (handler instanceof AbstractHttp11Protocol) {
    AbstractHttp11Protocol<?> protocol = (AbstractHttp11Protocol<?>) handler;
    Compression compression = getCompression();
    protocol.setCompression("on");
    protocol.setCompressionMinSize(compression.getMinResponseSize());
    configureCompressibleMimeTypes(protocol, compression);
    if (getCompression().getExcludedUserAgents() != null) {
      protocol.setNoCompressionUserAgents(
          StringUtils.arrayToCommaDelimitedString(
              getCompression().getExcludedUserAgents()));
    }
  }
}

Try setting a breakpoint on this method and debug your application to see if compression is actually enabled.

If not, it is very likely that there is some kind of wrong configuration in your project.

If it works, it indicates that your configuration is correct and that the problem is different.

If this is the case, before looking at anything else, it might be appropriate to try another server, such as Jetty or Undertow, which also support this compression feature, and see if everything works correctly there.

For instance, to configure Undertow instead of Tomcat you can use the following:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
    <exclusions>
        <exclusion>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-tomcat</artifactId>
        </exclusion>
    </exclusions>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-undertow</artifactId>
</dependency>

You can try to configure Tomcat compression programmatically as well; see matsev's answer in this stackoverflow question:

Using GZIP compression with Spring Boot/MVC/JavaConfig with RESTful

like image 118
jccampanero Avatar answered Oct 20 '22 19:10

jccampanero