Spring boot response compression not working

spring boot enable gzip response
spring boot 2 gzip
cdn spring boot
http2 spring boot
zuul gzip compression
spring boot cache static resources
spring boot undertow configuration
spring boot rest zip response

I have some javascript bundled file that is pretty big, ~1MB. I'm trying to turn on response compression with the following application properties in my yml file:

server.compression.enabled: true
server.compression.mime-types: application/json,application/xml,text/html,text/xml,text/plain,application/javascript,text/css

But it doesn't work. No compression is happening.

Request headers:

Connection: keep-alive
Pragma: no-cache
Cache-Control: no-cache
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/51.0.2704.103 Safari/537.36
Accept: */*
Accept-Encoding: gzip, deflate, sdch, br

Response headers

Cache-Control:no-cache, no-store, max-age=0, must-revalidate
Connection:keep-alive
Content-Length:842821
Content-Type:application/javascript;charset=UTF-8

There's no content encoding header in the response.

I'm using spring boot version 1.3.5.RELEASE

What am I missing?

=== EDIT 4 === I was planning to create a stand alone app to investigate further why content compression properties weren't working. But all of sudden it started working and I haven't changed any thing configuration-wise, not POM file change, not application.yml file change. So I don't know what has changed that made it working...

===EDIT 3=== follow @chimmi's suggestions further. I've put break points in the suggested places. It looks like requests to static resources (js files) never stopped at those break points. Only rest API requests do. And for those request, the content-length was zero for some reason which causes the content compression to be skipped.

===EDIT 2=== I've put a break point at line 180 of o.s.b.a.w.ServerProperties thanks to @chimmi's suggestion and it shows that all the properties are set but somehow the server doesn't honor the setting... :(

===EDIT 1===

not sure if it matters, but I'm pasting my application main and configuration code here:

Application.java:

@SpringBootApplication
public class TuangouApplication extends SpringBootServletInitializer {

    public static void main(String[] args) throws Exception {
        SpringApplication.run(TuangouApplication.class, args);
    }

    // this is for WAR file deployment
    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(TuangouApplication.class);
    }

    @Bean
    public javax.validation.Validator localValidatorFactoryBean() {
       return new LocalValidatorFactoryBean();
    }
}

Configuration:

@Configuration
public class TuangouConfiguration extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // @formatter:off   
        http.antMatcher("/**").authorizeRequests().antMatchers("/", "/login**").permitAll()
            .and().antMatcher("/**").authorizeRequests().antMatchers("/api/**").permitAll()
            .and().exceptionHandling().authenticationEntryPoint(new LoginUrlAuthenticationEntryPoint("/"))
            .and().formLogin().loginPage("/login").failureUrl("/login?error").permitAll()
            .and().logout().logoutSuccessUrl("/").permitAll()
            .and().csrf().csrfTokenRepository(csrfTokenRepository())
            .and().addFilterAfter(csrfHeaderFilter(), CsrfFilter.class)
            .headers().defaultsDisabled().cacheControl();
        // @formatter:on
    }

    @Order(Ordered.HIGHEST_PRECEDENCE)
    @Configuration
    @EnableGlobalMethodSecurity(prePostEnabled=true)
    protected static class AuthenticationSecurity extends GlobalAuthenticationConfigurerAdapter {

        @Override
        public void init(AuthenticationManagerBuilder auth) throws Exception {
          auth.userDetailsService(userDetailsService()).passwordEncoder(new BCryptPasswordEncoder());
        }

        @Bean
        public UserDetailsService userDetailsService() {
            return new DatabaseUserServiceDetails();
        }
    }

    private Filter csrfHeaderFilter() {
        return new OncePerRequestFilter() {
            @Override
            protected void doFilterInternal(HttpServletRequest request,
                    HttpServletResponse response, FilterChain filterChain)
                            throws ServletException, IOException {
                CsrfToken csrf = (CsrfToken) request
                        .getAttribute(CsrfToken.class.getName());
                if (csrf != null) {
                    Cookie cookie = WebUtils.getCookie(request, "XSRF-TOKEN");
                    String token = csrf.getToken();
                    if (cookie == null
                            || token != null && !token.equals(cookie.getValue())) {
                        cookie = new Cookie("XSRF-TOKEN", token);
                        cookie.setPath("/");
                        response.addCookie(cookie);
                    }
                }
                filterChain.doFilter(request, response);
            }
        };
    }

    private CsrfTokenRepository csrfTokenRepository() {
        HttpSessionCsrfTokenRepository repository = new HttpSessionCsrfTokenRepository();
        repository.setHeaderName("X-XSRF-TOKEN");
        return repository;
    }
}

Resource server config:

@Configuration
@EnableResourceServer
public class ResourceServerConfiguration extends ResourceServerConfigurerAdapter{

    @Autowired
    private TokenStore tokenStore;

    @Override
    public void configure(ResourceServerSecurityConfigurer resources)
            throws Exception {
        resources.tokenStore(tokenStore);
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
        // @formatter:off
        http.antMatcher("/**").authorizeRequests().antMatchers("/api/**").permitAll();
        // @formatter:on
    }
}

Maybe the problem is with YAML configuration. If you use ‘Starters’ SnakeYAML will be automatically provided via spring-boot-starter. If you don't - you must use properties convention in application.properties. Using YAML instead of Properties

EDIT: Try with this in your yml file:

server:
      compression:
        enabled: true
        mime-types: text/html,text/xml,text/plain,text/css,application/javascript,application/json
        min-response-size: 1024

HTTP Response compression not working with request accept , Tested this with Spring Boot 2.1.7 using Jetty and WebFlux. When using non-​reactive (so no WebFlux) the problem does not occur. TLDR; the server is not using compression when it should when the accept header with the mime-types contains mime-type; q=x. Tested this with Spring Boot 2.1.7 using Jetty and WebFlux. When using non-reactive (so no WebFlux) the problem does not occur. With compression enabled the application.properties contains mime-types e.g.

If you use non-embedded Tomcat you should add this to your server.xml:

compression="on" 
compressionMinSize="2048" 
compressableMimeType="text/html,text/xml,application/javascript"

More tomcat 8 config variables

Server Side Compression not working when sending Accept , When sending request as like this server compress response Spring Boot 2.0.x has reach the end of its life and is no longer supported. @zhaoyunxing92 there are a number of tests in Spring Boot that assert the response is not compressed if the min size isn't reached. It's hard to know where the problem is with the information you've provided.

Never had much luck with the Spring Boot compression. A simple solution could be to use a third party library like ziplet.

Add to pom.xml

<dependency>
    <groupId>com.github.ziplet</groupId>
    <artifactId>ziplet</artifactId>
    <version>2.0.0</version>
    <exclusions>
        <exclusion>
            <artifactId>servlet-api</artifactId>
            <groupId>javax.servlet</groupId>
        </exclusion>
    </exclusions>
</dependency>

Add to your @Config class :

@Bean
public Filter compressingFilter() {
    return new CompressingFilter();
}

How to enable GZIP compression in Spring Boot application , This kind of compression is disabled in Spring Boot by default but fortunately, we can enable it by setting below parameters in application. properties file. There should be Content-Encoding header with gzip value, also these files should be definitely smaller then before compression. Attchment is the sample project, when switching the container starter to jetty the response header contains the Content-Encoding with value gzip, and the content is comressed. But with undertow this does not.

Did you try with different browsers? That could be because of antivirus which is unzipping the file as mentioned in the SO post Spring boot http response compression doesn't work for some User-Agents

Spring Boot + GZIP Compression, In this example we will learn how to to enable compression for a Spring Boot application using GZIP. What is GZIP? Need for it? When a user hits the website a  November 11, 2016 · by Yogesh Prajapati · in Spring Boot · Leave a response Hi Guys, Spring boot provides a facility to compress your resources by changing minimum configuration.

you have to enable ssl like http2 mode, response compression (Content-Encoding) can work, when ssl mode is configured.

response compression

application.yml

server:
  compression:
     enabled: true
     mime-types: text/html,text/xml,text/plain,text/css, application/javascript, application/json
     min-response-size: 1024
  ssl:
   enabled: true
   key-store: keystore.p12
   key-store-password: pass
   keyStoreType: PKCS12
   keyAlias: name


spring:
  resources:   
      chain:
        gzipped: true

Spring Boot - REST response gzip compression, Learn to enable HTTP response compression in spring boot 2 applications. Love computers, programming and solving everyday problems. Find me on  1. Overview. Spring boot response compress or gzip can be enabled using server.compression.enabled in application.properties file, It will be supported for Tomcat, Jetty, and Undertow servers.

Spring boot response compress example, Spring boot response compress example for Tomcat, Jetty, and Undertow servers using different mime types using  It enables you to control compression by the request's user-agent, the response's size, and the response's mime type. If this doesn't meet your needs then I believe you will have to perform the compression in your controller and return a byte[] response with a gzip content-encoding header.

Configuring Spring Boot's Server, GZip compression, HTTP/2 , Configuring Spring Boot's Server, GZip compression, HTTP/2, caching and much more stuff for you so that you can get up and running quickly with your application. They must not be stored by a shared cache (e.g CDN). I am getting Content-Encoding = gzip in response headers Transferred JSON data size is reduced from 6.5MB to 1.2 MB - Great :-) But, the same code is NOT working in Internet Explorer 11.0.9600.18097.

POST requests not working after configuring compression on Spring , r/SpringBoot: Springboot. I am having a gzip problem with a Spring boot server. I activated compression on application.properties as follows:. It looks like GZIP compression is not working properly. It's configured for tomcat but it's not working for some reason # EMBEDDED SERVER CONFIGURATION server: compression: enabled: true min-response-size: 1024 mime-types: text/html, tex

Comments
  • Have you checked this SO -stackoverflow.com/questions/21410317/…
  • @aksappy yes i did. I based my solution on answer #2 from that link.
  • Your request headers have keep-alive, which indicate HTTP 1.0, but the referenced solution uses AbstractHttp11Protocol . Maybe you need to be sending HTTP 1.1 requests?
  • What server are you using ? Tomcat ? Jetty ? ....
  • @benjamin.d The code is deployed to AWS tomcat8
  • I tried the break point approach @chimmi suggested and it shows that all properties are read by spring boot container (I've updated my original post with the screenshot) but they are ignored somehow...
  • I guess he doesn't have a server.xml since he uses spring boot
  • I am having the same issue... I deploy my Spring Boot REST application to AWS Elastic Beanstalk (Tomcat instance), so there is no server.xml. Even though I specify Accept-Encoding: gzip, deflate, I don't see a Content-Encoding in the response. How do I work around this?
  • tried chrom, firefox, safari. all same behavior, no content compression. :(