From 8207a29e52bb7f9768f2e777317471a59b938a4d Mon Sep 17 00:00:00 2001 From: Rob Winch Date: Fri, 30 Oct 2015 10:55:45 -0500 Subject: [PATCH] SEC-3135: antMatchers(,new String[0]) now passive --- .../web/AbstractRequestMatcherRegistry.java | 17 ++- .../configurers/AuthorizeRequestsTests.java | 38 ++++--- .../HttpSecurityAntMatchersTests.java | 105 ++++++++++++++++++ 3 files changed, 144 insertions(+), 16 deletions(-) create mode 100644 config/src/test/java/org/springframework/security/config/annotation/web/configurers/HttpSecurityAntMatchersTests.java diff --git a/config/src/main/java/org/springframework/security/config/annotation/web/AbstractRequestMatcherRegistry.java b/config/src/main/java/org/springframework/security/config/annotation/web/AbstractRequestMatcherRegistry.java index bd8f5d0b00..b3f91cad03 100644 --- a/config/src/main/java/org/springframework/security/config/annotation/web/AbstractRequestMatcherRegistry.java +++ b/config/src/main/java/org/springframework/security/config/annotation/web/AbstractRequestMatcherRegistry.java @@ -52,6 +52,20 @@ public abstract class AbstractRequestMatcherRegistry { return requestMatchers(ANY_REQUEST); } + /** + * Maps a {@link List} of + * {@link org.springframework.security.web.util.matcher.AntPathRequestMatcher} + * instances. + * + * @param method the {@link HttpMethod} to use for any + * {@link HttpMethod}. + * + * @return the object that is chained after creating the {@link RequestMatcher} + */ + public C antMatchers(HttpMethod method) { + return antMatchers(method, new String[] { "/**" }); + } + /** * Maps a {@link List} of {@link org.springframework.security.web.util.matcher.AntPathRequestMatcher} instances. * @@ -144,9 +158,6 @@ public abstract class AbstractRequestMatcherRegistry { */ public static List antMatchers(HttpMethod httpMethod, String...antPatterns) { String method = httpMethod == null ? null : httpMethod.toString(); - if(ObjectUtils.isEmpty(antPatterns)) { - antPatterns = new String[] { "/**" }; - } List matchers = new ArrayList(); for(String pattern : antPatterns) { matchers.add(new AntPathRequestMatcher(pattern, method)); diff --git a/config/src/test/java/org/springframework/security/config/annotation/web/configurers/AuthorizeRequestsTests.java b/config/src/test/java/org/springframework/security/config/annotation/web/configurers/AuthorizeRequestsTests.java index d72c2b9e79..7814ef7e11 100644 --- a/config/src/test/java/org/springframework/security/config/annotation/web/configurers/AuthorizeRequestsTests.java +++ b/config/src/test/java/org/springframework/security/config/annotation/web/configurers/AuthorizeRequestsTests.java @@ -19,9 +19,9 @@ import static org.fest.assertions.Assertions.assertThat; import javax.servlet.http.HttpServletResponse; +import org.junit.After; import org.junit.Before; import org.junit.Test; -import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Configuration; import org.springframework.http.HttpMethod; @@ -33,23 +33,17 @@ import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; import org.springframework.security.web.FilterChainProxy; -import org.springframework.test.context.ContextConfiguration; -import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; -import org.springframework.test.context.web.WebAppConfiguration; +import org.springframework.web.context.support.AnnotationConfigWebApplicationContext; /** * @author Rob Winch * */ -@RunWith(SpringJUnit4ClassRunner.class) -@ContextConfiguration -@WebAppConfiguration public class AuthorizeRequestsTests { - @Autowired - MockHttpServletRequest request; - @Autowired - MockHttpServletResponse response; + AnnotationConfigWebApplicationContext context; + MockHttpServletRequest request; + MockHttpServletResponse response; MockFilterChain chain; @Autowired @@ -57,12 +51,22 @@ public class AuthorizeRequestsTests { @Before public void setup() { + request = new MockHttpServletRequest(); + response = new MockHttpServletResponse(); chain = new MockFilterChain(); } + @After + public void cleanup() { + if(context != null) { + context.close(); + } + } + // SEC-3135 @Test public void antMatchersMethodAndNoPatterns() throws Exception { + loadConfig(AntMatchersNoPatternsConfig.class); request.setMethod("POST"); springSecurityFilterChain.doFilter(request, response, chain); @@ -72,7 +76,7 @@ public class AuthorizeRequestsTests { @EnableWebSecurity @Configuration - static class Config extends WebSecurityConfigurerAdapter { + static class AntMatchersNoPatternsConfig extends WebSecurityConfigurerAdapter { protected void configure(HttpSecurity http) throws Exception { http .authorizeRequests() @@ -85,4 +89,12 @@ public class AuthorizeRequestsTests { .inMemoryAuthentication(); } } -} + + public void loadConfig(Class... configs) { + context = new AnnotationConfigWebApplicationContext(); + context.register(configs); + context.refresh(); + + context.getAutowireCapableBeanFactory().autowireBean(this); + } +} \ No newline at end of file diff --git a/config/src/test/java/org/springframework/security/config/annotation/web/configurers/HttpSecurityAntMatchersTests.java b/config/src/test/java/org/springframework/security/config/annotation/web/configurers/HttpSecurityAntMatchersTests.java new file mode 100644 index 0000000000..a5ba1a75ee --- /dev/null +++ b/config/src/test/java/org/springframework/security/config/annotation/web/configurers/HttpSecurityAntMatchersTests.java @@ -0,0 +1,105 @@ +/* + * Copyright 2002-2015 the original author or authors. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.springframework.security.config.annotation.web.configurers; + +import static org.fest.assertions.Assertions.assertThat; + +import javax.servlet.http.HttpServletResponse; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Configuration; +import org.springframework.http.HttpMethod; +import org.springframework.mock.web.MockFilterChain; +import org.springframework.mock.web.MockHttpServletRequest; +import org.springframework.mock.web.MockHttpServletResponse; +import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; +import org.springframework.security.config.annotation.web.builders.HttpSecurity; +import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; +import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; +import org.springframework.security.web.FilterChainProxy; +import org.springframework.web.context.support.AnnotationConfigWebApplicationContext; + +/** + * @author Rob Winch + * + */ +public class HttpSecurityAntMatchersTests { + AnnotationConfigWebApplicationContext context; + + MockHttpServletRequest request; + MockHttpServletResponse response; + MockFilterChain chain; + + @Autowired + FilterChainProxy springSecurityFilterChain; + + @Before + public void setup() { + request = new MockHttpServletRequest(); + response = new MockHttpServletResponse(); + chain = new MockFilterChain(); + } + + @After + public void cleanup() { + if(context != null) { + context.close(); + } + } + + // SEC-3135 + @Test + public void antMatchersMethodAndNoPatterns() throws Exception { + loadConfig(AntMatchersNoPatternsConfig.class); + request.setMethod("POST"); + + springSecurityFilterChain.doFilter(request, response, chain); + + assertThat(response.getStatus()).isEqualTo(HttpServletResponse.SC_FORBIDDEN); + } + + @EnableWebSecurity + @Configuration + static class AntMatchersNoPatternsConfig extends WebSecurityConfigurerAdapter { + protected void configure(HttpSecurity http) throws Exception { + http + .requestMatchers() + .antMatchers(HttpMethod.POST) + .and() + .authorizeRequests() + .anyRequest().denyAll(); + } + + @Override + protected void configure(AuthenticationManagerBuilder auth) throws Exception { + auth + .inMemoryAuthentication(); + } + } + + public void loadConfig(Class... configs) { + context = new AnnotationConfigWebApplicationContext(); + context.register(configs); + context.refresh(); + + context.getAutowireCapableBeanFactory().autowireBean(this); + } + + +}