diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerServletWebConfiguration.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerServletWebConfiguration.java index 3cf800e169..b025ccb414 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerServletWebConfiguration.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerServletWebConfiguration.java @@ -25,6 +25,7 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication; import org.springframework.boot.autoconfigure.web.ConditionalOnEnabledResourceChain; +import org.springframework.boot.autoconfigure.web.servlet.ConditionalOnMissingFilterBean; import org.springframework.boot.autoconfigure.web.servlet.WebMvcAutoConfiguration; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; @@ -74,8 +75,8 @@ class FreeMarkerServletWebConfiguration extends AbstractFreeMarkerConfiguration } @Bean - @ConditionalOnMissingBean(ResourceUrlEncodingFilter.class) @ConditionalOnEnabledResourceChain + @ConditionalOnMissingFilterBean(ResourceUrlEncodingFilter.class) public FilterRegistrationBean resourceUrlEncodingFilter() { FilterRegistrationBean registration = new FilterRegistrationBean<>( new ResourceUrlEncodingFilter()); diff --git a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafAutoConfiguration.java b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafAutoConfiguration.java index b3c1299e3a..a1b1c3b185 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafAutoConfiguration.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafAutoConfiguration.java @@ -50,6 +50,7 @@ import org.springframework.boot.autoconfigure.template.TemplateLocation; import org.springframework.boot.autoconfigure.thymeleaf.ThymeleafProperties.Reactive; import org.springframework.boot.autoconfigure.web.ConditionalOnEnabledResourceChain; import org.springframework.boot.autoconfigure.web.reactive.WebFluxAutoConfiguration; +import org.springframework.boot.autoconfigure.web.servlet.ConditionalOnMissingFilterBean; import org.springframework.boot.autoconfigure.web.servlet.WebMvcAutoConfiguration; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.context.properties.PropertyMapper; @@ -169,8 +170,8 @@ public class ThymeleafAutoConfiguration { static class ThymeleafWebMvcConfiguration { @Bean - @ConditionalOnMissingBean(ResourceUrlEncodingFilter.class) @ConditionalOnEnabledResourceChain + @ConditionalOnMissingFilterBean(ResourceUrlEncodingFilter.class) public FilterRegistrationBean resourceUrlEncodingFilter() { FilterRegistrationBean registration = new FilterRegistrationBean<>( new ResourceUrlEncodingFilter()); diff --git a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerAutoConfigurationServletIntegrationTests.java b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerAutoConfigurationServletIntegrationTests.java index 617343a42e..f9cd6d84ec 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerAutoConfigurationServletIntegrationTests.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/freemarker/FreeMarkerAutoConfigurationServletIntegrationTests.java @@ -173,7 +173,7 @@ public class FreeMarkerAutoConfigurationServletIntegrationTests { @SuppressWarnings("rawtypes") public void registerResourceHandlingFilterWithOtherRegistrationBean() { // gh-14897 - load(FilterRegistrationConfiguration.class, + load(FilterRegistrationOtherConfiguration.class, "spring.resources.chain.enabled:true"); Map beans = this.context .getBeansOfType(FilterRegistrationBean.class); @@ -185,6 +185,22 @@ public class FreeMarkerAutoConfigurationServletIntegrationTests { EnumSet.of(DispatcherType.REQUEST, DispatcherType.ERROR)); } + @Test + @SuppressWarnings("rawtypes") + public void registerResourceHandlingFilterWithResourceRegistrationBean() { + // gh-14926 + load(FilterRegistrationResourceConfiguration.class, + "spring.resources.chain.enabled:true"); + Map beans = this.context + .getBeansOfType(FilterRegistrationBean.class); + assertThat(beans).hasSize(1); + FilterRegistrationBean registration = beans.values().stream() + .filter((r) -> r.getFilter() instanceof ResourceUrlEncodingFilter) + .findFirst().get(); + assertThat(registration).hasFieldOrPropertyWithValue("dispatcherTypes", + EnumSet.of(DispatcherType.INCLUDE)); + } + private void load(String... env) { load(BaseConfiguration.class, env); } @@ -223,7 +239,21 @@ public class FreeMarkerAutoConfigurationServletIntegrationTests { @Configuration @Import(BaseConfiguration.class) - static class FilterRegistrationConfiguration { + static class FilterRegistrationResourceConfiguration { + + @Bean + public FilterRegistrationBean filterRegisration() { + FilterRegistrationBean bean = new FilterRegistrationBean( + new ResourceUrlEncodingFilter()); + bean.setDispatcherTypes(EnumSet.of(DispatcherType.INCLUDE)); + return bean; + } + + } + + @Configuration + @Import(BaseConfiguration.class) + static class FilterRegistrationOtherConfiguration { @Bean public FilterRegistrationBean filterRegisration() { diff --git a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafServletAutoConfigurationTests.java b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafServletAutoConfigurationTests.java index abf4da93b1..f0539bd061 100644 --- a/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafServletAutoConfigurationTests.java +++ b/spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/thymeleaf/ThymeleafServletAutoConfigurationTests.java @@ -281,7 +281,7 @@ public class ThymeleafServletAutoConfigurationTests { @SuppressWarnings("rawtypes") public void registerResourceHandlingFilterWithOtherRegistrationBean() { // gh-14897 - load(FilterRegistrationConfiguration.class, + load(FilterRegistrationOtherConfiguration.class, "spring.resources.chain.enabled:true"); Map beans = this.context .getBeansOfType(FilterRegistrationBean.class); @@ -293,6 +293,22 @@ public class ThymeleafServletAutoConfigurationTests { EnumSet.of(DispatcherType.REQUEST, DispatcherType.ERROR)); } + @Test + @SuppressWarnings("rawtypes") + public void registerResourceHandlingFilterWithResourceRegistrationBean() { + // gh-14926 + load(FilterRegistrationResourceConfiguration.class, + "spring.resources.chain.enabled:true"); + Map beans = this.context + .getBeansOfType(FilterRegistrationBean.class); + assertThat(beans).hasSize(1); + FilterRegistrationBean registration = beans.values().stream() + .filter((r) -> r.getFilter() instanceof ResourceUrlEncodingFilter) + .findFirst().get(); + assertThat(registration).hasFieldOrPropertyWithValue("dispatcherTypes", + EnumSet.of(DispatcherType.INCLUDE)); + } + @Test public void layoutDialectCanBeCustomized() { load(LayoutDialectConfiguration.class); @@ -337,7 +353,21 @@ public class ThymeleafServletAutoConfigurationTests { @Configuration @Import(BaseConfiguration.class) - static class FilterRegistrationConfiguration { + static class FilterRegistrationResourceConfiguration { + + @Bean + public FilterRegistrationBean filterRegisration() { + FilterRegistrationBean bean = new FilterRegistrationBean( + new ResourceUrlEncodingFilter()); + bean.setDispatcherTypes(EnumSet.of(DispatcherType.INCLUDE)); + return bean; + } + + } + + @Configuration + @Import(BaseConfiguration.class) + static class FilterRegistrationOtherConfiguration { @Bean public FilterRegistrationBean filterRegisration() {