Reformat code using spring-javaformat
Run `./gradlew format` to reformat all java files. Issue gh-8945
This commit is contained in:
@@ -25,19 +25,19 @@ import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||
* @author Luke Taylor
|
||||
*/
|
||||
public class BeanNameCollectingPostProcessor implements BeanPostProcessor {
|
||||
|
||||
Set<String> beforeInitPostProcessedBeans = new HashSet<>();
|
||||
|
||||
Set<String> afterInitPostProcessedBeans = new HashSet<>();
|
||||
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
|
||||
if (beanName != null) {
|
||||
beforeInitPostProcessedBeans.add(beanName);
|
||||
}
|
||||
return bean;
|
||||
}
|
||||
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
|
||||
if (beanName != null) {
|
||||
afterInitPostProcessedBeans.add(beanName);
|
||||
}
|
||||
@@ -51,4 +51,5 @@ public class BeanNameCollectingPostProcessor implements BeanPostProcessor {
|
||||
public Set<String> getAfterInitPostProcessedBeans() {
|
||||
return afterInitPostProcessedBeans;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -30,9 +30,13 @@ import org.springframework.security.authentication.event.AbstractAuthenticationF
|
||||
* @since 3.1
|
||||
*/
|
||||
public class CollectingAppListener implements ApplicationListener {
|
||||
|
||||
Set<ApplicationEvent> events = new HashSet<>();
|
||||
|
||||
Set<AbstractAuthenticationEvent> authenticationEvents = new HashSet<>();
|
||||
|
||||
Set<AbstractAuthenticationFailureEvent> authenticationFailureEvents = new HashSet<>();
|
||||
|
||||
Set<AbstractAuthorizationEvent> authorizationEvents = new HashSet<>();
|
||||
|
||||
public void onApplicationEvent(ApplicationEvent event) {
|
||||
@@ -65,4 +69,5 @@ public class CollectingAppListener implements ApplicationListener {
|
||||
public Set<AbstractAuthorizationEvent> getAuthorizationEvents() {
|
||||
return authorizationEvents;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -16,14 +16,13 @@
|
||||
package org.springframework.security.config;
|
||||
|
||||
public abstract class ConfigTestUtils {
|
||||
|
||||
public static final String AUTH_PROVIDER_XML = "<authentication-manager alias='authManager'>"
|
||||
+ " <authentication-provider>"
|
||||
+ " <user-service id='us'>"
|
||||
+ " <authentication-provider>" + " <user-service id='us'>"
|
||||
+ " <user name='bob' password='{noop}bobspassword' authorities='ROLE_A,ROLE_B' />"
|
||||
+ " <user name='bill' password='{noop}billspassword' authorities='ROLE_A,ROLE_B,AUTH_OTHER' />"
|
||||
+ " <user name='admin' password='{noop}password' authorities='ROLE_ADMIN,ROLE_USER' />"
|
||||
+ " <user name='user' password='{noop}password' authorities='ROLE_USER' />"
|
||||
+ " </user-service>"
|
||||
+ " </authentication-provider>"
|
||||
+ "</authentication-manager>";
|
||||
+ " </user-service>" + " </authentication-provider>" + "</authentication-manager>";
|
||||
|
||||
}
|
||||
|
||||
@@ -27,6 +27,7 @@ import org.springframework.util.Assert;
|
||||
* @author Ben Alex
|
||||
*/
|
||||
public class DataSourcePopulator implements InitializingBean {
|
||||
|
||||
// ~ Instance fields
|
||||
// ================================================================================================
|
||||
|
||||
@@ -35,8 +36,10 @@ public class DataSourcePopulator implements InitializingBean {
|
||||
public void afterPropertiesSet() {
|
||||
Assert.notNull(template, "dataSource required");
|
||||
|
||||
template.execute("CREATE TABLE USERS(USERNAME VARCHAR_IGNORECASE(50) NOT NULL PRIMARY KEY,PASSWORD VARCHAR_IGNORECASE(500) NOT NULL,ENABLED BOOLEAN NOT NULL);");
|
||||
template.execute("CREATE TABLE AUTHORITIES(USERNAME VARCHAR_IGNORECASE(50) NOT NULL,AUTHORITY VARCHAR_IGNORECASE(50) NOT NULL,CONSTRAINT FK_AUTHORITIES_USERS FOREIGN KEY(USERNAME) REFERENCES USERS(USERNAME));");
|
||||
template.execute(
|
||||
"CREATE TABLE USERS(USERNAME VARCHAR_IGNORECASE(50) NOT NULL PRIMARY KEY,PASSWORD VARCHAR_IGNORECASE(500) NOT NULL,ENABLED BOOLEAN NOT NULL);");
|
||||
template.execute(
|
||||
"CREATE TABLE AUTHORITIES(USERNAME VARCHAR_IGNORECASE(50) NOT NULL,AUTHORITY VARCHAR_IGNORECASE(50) NOT NULL,CONSTRAINT FK_AUTHORITIES_USERS FOREIGN KEY(USERNAME) REFERENCES USERS(USERNAME));");
|
||||
template.execute("CREATE UNIQUE INDEX IX_AUTH_USERNAME ON AUTHORITIES(USERNAME,AUTHORITY);");
|
||||
|
||||
/*
|
||||
@@ -66,4 +69,5 @@ public class DataSourcePopulator implements InitializingBean {
|
||||
public void setDataSource(DataSource dataSource) {
|
||||
this.template = new JdbcTemplate(dataSource);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -50,6 +50,7 @@ import org.springframework.security.web.util.matcher.AnyRequestMatcher;
|
||||
* @author Ben Alex
|
||||
*/
|
||||
public class FilterChainProxyConfigTests {
|
||||
|
||||
private ClassPathXmlApplicationContext appCtx;
|
||||
|
||||
// ~ Methods
|
||||
@@ -59,8 +60,7 @@ public class FilterChainProxyConfigTests {
|
||||
public void loadContext() {
|
||||
System.setProperty("sec1235.pattern1", "/login");
|
||||
System.setProperty("sec1235.pattern2", "/logout");
|
||||
appCtx = new ClassPathXmlApplicationContext(
|
||||
"org/springframework/security/util/filtertest-valid.xml");
|
||||
appCtx = new ClassPathXmlApplicationContext("org/springframework/security/util/filtertest-valid.xml");
|
||||
}
|
||||
|
||||
@After
|
||||
@@ -72,15 +72,13 @@ public class FilterChainProxyConfigTests {
|
||||
|
||||
@Test
|
||||
public void normalOperation() throws Exception {
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("filterChain",
|
||||
FilterChainProxy.class);
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("filterChain", FilterChainProxy.class);
|
||||
doNormalOperation(filterChainProxy);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void normalOperationWithNewConfig() throws Exception {
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxy",
|
||||
FilterChainProxy.class);
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxy", FilterChainProxy.class);
|
||||
filterChainProxy.setFirewall(new DefaultHttpFirewall());
|
||||
checkPathAndFilterOrder(filterChainProxy);
|
||||
doNormalOperation(filterChainProxy);
|
||||
@@ -88,8 +86,7 @@ public class FilterChainProxyConfigTests {
|
||||
|
||||
@Test
|
||||
public void normalOperationWithNewConfigRegex() throws Exception {
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxyRegex",
|
||||
FilterChainProxy.class);
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxyRegex", FilterChainProxy.class);
|
||||
filterChainProxy.setFirewall(new DefaultHttpFirewall());
|
||||
checkPathAndFilterOrder(filterChainProxy);
|
||||
doNormalOperation(filterChainProxy);
|
||||
@@ -97,8 +94,7 @@ public class FilterChainProxyConfigTests {
|
||||
|
||||
@Test
|
||||
public void normalOperationWithNewConfigNonNamespace() throws Exception {
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean(
|
||||
"newFilterChainProxyNonNamespace", FilterChainProxy.class);
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxyNonNamespace", FilterChainProxy.class);
|
||||
filterChainProxy.setFirewall(new DefaultHttpFirewall());
|
||||
checkPathAndFilterOrder(filterChainProxy);
|
||||
doNormalOperation(filterChainProxy);
|
||||
@@ -106,26 +102,24 @@ public class FilterChainProxyConfigTests {
|
||||
|
||||
@Test
|
||||
public void pathWithNoMatchHasNoFilters() {
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean(
|
||||
"newFilterChainProxyNoDefaultPath", FilterChainProxy.class);
|
||||
FilterChainProxy filterChainProxy = appCtx.getBean("newFilterChainProxyNoDefaultPath", FilterChainProxy.class);
|
||||
assertThat(filterChainProxy.getFilters("/nomatch")).isNull();
|
||||
}
|
||||
|
||||
// SEC-1235
|
||||
@Test
|
||||
public void mixingPatternsAndPlaceholdersDoesntCauseOrderingIssues() {
|
||||
FilterChainProxy fcp = appCtx.getBean("sec1235FilterChainProxy",
|
||||
FilterChainProxy.class);
|
||||
FilterChainProxy fcp = appCtx.getBean("sec1235FilterChainProxy", FilterChainProxy.class);
|
||||
|
||||
List<SecurityFilterChain> chains = fcp.getFilterChains();
|
||||
assertThat(getPattern(chains.get(0))).isEqualTo("/login*");
|
||||
assertThat(getPattern(chains.get(1))).isEqualTo("/logout");
|
||||
assertThat(((DefaultSecurityFilterChain) chains.get(2)).getRequestMatcher() instanceof AnyRequestMatcher).isTrue();
|
||||
assertThat(((DefaultSecurityFilterChain) chains.get(2)).getRequestMatcher() instanceof AnyRequestMatcher)
|
||||
.isTrue();
|
||||
}
|
||||
|
||||
private String getPattern(SecurityFilterChain chain) {
|
||||
return ((AntPathRequestMatcher) ((DefaultSecurityFilterChain) chain)
|
||||
.getRequestMatcher()).getPattern();
|
||||
return ((AntPathRequestMatcher) ((DefaultSecurityFilterChain) chain).getRequestMatcher()).getPattern();
|
||||
}
|
||||
|
||||
private void checkPathAndFilterOrder(FilterChainProxy filterChainProxy) {
|
||||
@@ -158,13 +152,12 @@ public class FilterChainProxyConfigTests {
|
||||
FilterChain chain = mock(FilterChain.class);
|
||||
|
||||
filterChainProxy.doFilter(request, response, chain);
|
||||
verify(chain).doFilter(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class));
|
||||
verify(chain).doFilter(any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
|
||||
request.setServletPath("/a/path/which/doesnt/match/any/filter.html");
|
||||
chain = mock(FilterChain.class);
|
||||
filterChainProxy.doFilter(request, response, chain);
|
||||
verify(chain).doFilter(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class));
|
||||
verify(chain).doFilter(any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -34,6 +34,7 @@ import org.springframework.security.config.util.InMemoryXmlApplicationContext;
|
||||
* @author Luke Taylor
|
||||
*/
|
||||
public class InvalidConfigurationTests {
|
||||
|
||||
private InMemoryXmlApplicationContext appContext;
|
||||
|
||||
@After
|
||||
@@ -65,8 +66,7 @@ public class InvalidConfigurationTests {
|
||||
assertThat(cause instanceof NoSuchBeanDefinitionException).isTrue();
|
||||
NoSuchBeanDefinitionException nsbe = (NoSuchBeanDefinitionException) cause;
|
||||
assertThat(nsbe.getBeanName()).isEqualTo(BeanIds.AUTHENTICATION_MANAGER);
|
||||
assertThat(nsbe.getMessage()).endsWith(
|
||||
AuthenticationManagerFactoryBean.MISSING_BEAN_ERROR_MESSAGE);
|
||||
assertThat(nsbe.getMessage()).endsWith(AuthenticationManagerFactoryBean.MISSING_BEAN_ERROR_MESSAGE);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -80,4 +80,5 @@ public class InvalidConfigurationTests {
|
||||
private void setContext(String context) {
|
||||
appContext = new InMemoryXmlApplicationContext(context);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -24,9 +24,8 @@ import org.springframework.security.core.Authentication;
|
||||
|
||||
public class MockAfterInvocationProvider implements AfterInvocationProvider {
|
||||
|
||||
public Object decide(Authentication authentication, Object object,
|
||||
Collection<ConfigAttribute> config, Object returnedObject)
|
||||
throws AccessDeniedException {
|
||||
public Object decide(Authentication authentication, Object object, Collection<ConfigAttribute> config,
|
||||
Object returnedObject) throws AccessDeniedException {
|
||||
return returnedObject;
|
||||
}
|
||||
|
||||
|
||||
@@ -26,8 +26,8 @@ import java.util.List;
|
||||
* @author Rob Winch
|
||||
* @since 5.0.2
|
||||
*/
|
||||
public class MockEventListener<T extends ApplicationEvent>
|
||||
implements ApplicationListener<T> {
|
||||
public class MockEventListener<T extends ApplicationEvent> implements ApplicationListener<T> {
|
||||
|
||||
private List<T> events = new ArrayList<>();
|
||||
|
||||
public void onApplicationEvent(T event) {
|
||||
@@ -37,4 +37,5 @@ public class MockEventListener<T extends ApplicationEvent>
|
||||
public List<T> getEvents() {
|
||||
return this.events;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -26,8 +26,8 @@ import org.springframework.transaction.TransactionStatus;
|
||||
* @author Luke Taylor
|
||||
*/
|
||||
public class MockTransactionManager implements PlatformTransactionManager {
|
||||
public TransactionStatus getTransaction(TransactionDefinition definition)
|
||||
throws TransactionException {
|
||||
|
||||
public TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException {
|
||||
return mock(TransactionStatus.class);
|
||||
}
|
||||
|
||||
@@ -36,4 +36,5 @@ public class MockTransactionManager implements PlatformTransactionManager {
|
||||
|
||||
public void rollback(TransactionStatus status) throws TransactionException {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -26,18 +26,16 @@ import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||
*/
|
||||
public class MockUserServiceBeanPostProcessor implements BeanPostProcessor {
|
||||
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
|
||||
return bean;
|
||||
}
|
||||
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
|
||||
if (bean instanceof PostProcessedMockUserDetailsService) {
|
||||
((PostProcessedMockUserDetailsService) bean)
|
||||
.setPostProcessorWasHere("Hello from the post processor!");
|
||||
((PostProcessedMockUserDetailsService) bean).setPostProcessorWasHere("Hello from the post processor!");
|
||||
}
|
||||
|
||||
return bean;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import org.springframework.security.core.userdetails.UserDetails;
|
||||
import org.springframework.security.core.userdetails.UserDetailsService;
|
||||
|
||||
public class PostProcessedMockUserDetailsService implements UserDetailsService {
|
||||
|
||||
private String postProcessorWasHere;
|
||||
|
||||
public PostProcessedMockUserDetailsService() {
|
||||
@@ -36,4 +37,5 @@ public class PostProcessedMockUserDetailsService implements UserDetailsService {
|
||||
public UserDetails loadUserByUsername(String username) {
|
||||
throw new UnsupportedOperationException("Not for actual use");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -41,7 +41,6 @@ import static org.powermock.api.mockito.PowerMockito.verifyStatic;
|
||||
import static org.powermock.api.mockito.PowerMockito.verifyZeroInteractions;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Luke Taylor
|
||||
* @author Rob Winch
|
||||
* @since 3.0
|
||||
@@ -50,15 +49,16 @@ import static org.powermock.api.mockito.PowerMockito.verifyZeroInteractions;
|
||||
@PrepareForTest({ ClassUtils.class })
|
||||
@PowerMockIgnore({ "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*" })
|
||||
public class SecurityNamespaceHandlerTests {
|
||||
|
||||
@Rule
|
||||
public ExpectedException thrown = ExpectedException.none();
|
||||
|
||||
private static final String XML_AUTHENTICATION_MANAGER = "<authentication-manager>"
|
||||
+ " <authentication-provider>" + " <user-service id='us'>"
|
||||
+ " <user name='bob' password='bobspassword' authorities='ROLE_A' />"
|
||||
+ " </user-service>" + " </authentication-provider>"
|
||||
+ "</authentication-manager>";
|
||||
private static final String XML_AUTHENTICATION_MANAGER = "<authentication-manager>" + " <authentication-provider>"
|
||||
+ " <user-service id='us'>" + " <user name='bob' password='bobspassword' authorities='ROLE_A' />"
|
||||
+ " </user-service>" + " </authentication-provider>" + "</authentication-manager>";
|
||||
|
||||
private static final String XML_HTTP_BLOCK = "<http auto-config='true'/>";
|
||||
|
||||
private static final String FILTER_CHAIN_PROXY_CLASSNAME = "org.springframework.security.web.FilterChainProxy";
|
||||
|
||||
@Test
|
||||
@@ -74,15 +74,13 @@ public class SecurityNamespaceHandlerTests {
|
||||
@Test
|
||||
public void pre32SchemaAreNotSupported() {
|
||||
try {
|
||||
new InMemoryXmlApplicationContext(
|
||||
"<user-service id='us'>"
|
||||
+ " <user name='bob' password='bobspassword' authorities='ROLE_A' />"
|
||||
+ "</user-service>", "3.0.3", null);
|
||||
new InMemoryXmlApplicationContext("<user-service id='us'>"
|
||||
+ " <user name='bob' password='bobspassword' authorities='ROLE_A' />" + "</user-service>", "3.0.3",
|
||||
null);
|
||||
fail("Expected BeanDefinitionParsingException");
|
||||
}
|
||||
catch (BeanDefinitionParsingException expected) {
|
||||
assertThat(expected.getMessage().contains(
|
||||
"You cannot use a spring-security-2.0.xsd"));
|
||||
assertThat(expected.getMessage().contains("You cannot use a spring-security-2.0.xsd"));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -91,8 +89,8 @@ public class SecurityNamespaceHandlerTests {
|
||||
public void initDoesNotLogErrorWhenFilterChainProxyFailsToLoad() throws Exception {
|
||||
String className = "javax.servlet.Filter";
|
||||
spy(ClassUtils.class);
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName",
|
||||
eq(FILTER_CHAIN_PROXY_CLASSNAME), any(ClassLoader.class));
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName", eq(FILTER_CHAIN_PROXY_CLASSNAME),
|
||||
any(ClassLoader.class));
|
||||
|
||||
Log logger = mock(Log.class);
|
||||
SecurityNamespaceHandler handler = new SecurityNamespaceHandler();
|
||||
@@ -111,8 +109,8 @@ public class SecurityNamespaceHandlerTests {
|
||||
thrown.expect(BeanDefinitionParsingException.class);
|
||||
thrown.expectMessage("NoClassDefFoundError: " + className);
|
||||
spy(ClassUtils.class);
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName",
|
||||
eq(FILTER_CHAIN_PROXY_CLASSNAME), any(ClassLoader.class));
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName", eq(FILTER_CHAIN_PROXY_CLASSNAME),
|
||||
any(ClassLoader.class));
|
||||
new InMemoryXmlApplicationContext(XML_AUTHENTICATION_MANAGER + XML_HTTP_BLOCK);
|
||||
}
|
||||
|
||||
@@ -120,8 +118,8 @@ public class SecurityNamespaceHandlerTests {
|
||||
public void filterNoClassDefFoundErrorNoHttpBlock() throws Exception {
|
||||
String className = "javax.servlet.Filter";
|
||||
spy(ClassUtils.class);
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName",
|
||||
eq(FILTER_CHAIN_PROXY_CLASSNAME), any(ClassLoader.class));
|
||||
doThrow(new NoClassDefFoundError(className)).when(ClassUtils.class, "forName", eq(FILTER_CHAIN_PROXY_CLASSNAME),
|
||||
any(ClassLoader.class));
|
||||
new InMemoryXmlApplicationContext(XML_AUTHENTICATION_MANAGER);
|
||||
// should load just fine since no http block
|
||||
}
|
||||
@@ -151,9 +149,10 @@ public class SecurityNamespaceHandlerTests {
|
||||
public void websocketNotFoundExceptionNoMessageBlock() throws Exception {
|
||||
String className = FILTER_CHAIN_PROXY_CLASSNAME;
|
||||
spy(ClassUtils.class);
|
||||
doThrow(new ClassNotFoundException(className)).when(ClassUtils.class, "forName",
|
||||
eq(Message.class.getName()), any(ClassLoader.class));
|
||||
doThrow(new ClassNotFoundException(className)).when(ClassUtils.class, "forName", eq(Message.class.getName()),
|
||||
any(ClassLoader.class));
|
||||
new InMemoryXmlApplicationContext(XML_AUTHENTICATION_MANAGER);
|
||||
// should load just fine since no websocket block
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -29,4 +29,5 @@ public interface TestBusinessBean {
|
||||
void doSomething();
|
||||
|
||||
void unprotected();
|
||||
|
||||
}
|
||||
|
||||
@@ -21,8 +21,8 @@ import org.springframework.security.core.session.SessionCreationEvent;
|
||||
/**
|
||||
* @author Luke Taylor
|
||||
*/
|
||||
public class TestBusinessBeanImpl implements TestBusinessBean,
|
||||
ApplicationListener<SessionCreationEvent> {
|
||||
public class TestBusinessBeanImpl implements TestBusinessBean, ApplicationListener<SessionCreationEvent> {
|
||||
|
||||
public void setInteger(int i) {
|
||||
}
|
||||
|
||||
@@ -46,4 +46,5 @@ public class TestBusinessBeanImpl implements TestBusinessBean,
|
||||
public void onApplicationEvent(SessionCreationEvent event) {
|
||||
System.out.println(event);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ import org.springframework.transaction.annotation.Transactional;
|
||||
* @author Luke Taylor
|
||||
*/
|
||||
public class TransactionalTestBusinessBean implements TestBusinessBean {
|
||||
|
||||
public void setInteger(int i) {
|
||||
}
|
||||
|
||||
@@ -37,4 +38,5 @@ public class TransactionalTestBusinessBean implements TestBusinessBean {
|
||||
|
||||
public void unprotected() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -22,8 +22,8 @@ import java.util.List;
|
||||
* @author Rob Winch
|
||||
*
|
||||
*/
|
||||
class ConcereteSecurityConfigurerAdapter extends
|
||||
SecurityConfigurerAdapter<Object, SecurityBuilder<Object>> {
|
||||
class ConcereteSecurityConfigurerAdapter extends SecurityConfigurerAdapter<Object, SecurityBuilder<Object>> {
|
||||
|
||||
private List<Object> list = new ArrayList<>();
|
||||
|
||||
@Override
|
||||
@@ -35,4 +35,5 @@ class ConcereteSecurityConfigurerAdapter extends
|
||||
this.list = l;
|
||||
return this;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -32,8 +32,7 @@ public class ObjectPostProcessorTests {
|
||||
|
||||
@Test
|
||||
public void convertTypes() {
|
||||
assertThat((Object) PerformConversion.perform(new ArrayList<>()))
|
||||
.isInstanceOf(LinkedList.class);
|
||||
assertThat((Object) PerformConversion.perform(new ArrayList<>())).isInstanceOf(LinkedList.class);
|
||||
}
|
||||
|
||||
static class ListToLinkedListObjectPostProcessor implements ObjectPostProcessor<List<?>> {
|
||||
@@ -41,13 +40,15 @@ public class ObjectPostProcessorTests {
|
||||
public <O extends List<?>> O postProcess(O l) {
|
||||
return (O) new LinkedList(l);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class PerformConversion {
|
||||
|
||||
public static List<?> perform(ArrayList<?> l) {
|
||||
return new ListToLinkedListObjectPostProcessor().postProcess(l);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package org.springframework.security.config.annotation;
|
||||
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
@@ -30,6 +29,7 @@ import static org.mockito.Mockito.mock;
|
||||
*
|
||||
*/
|
||||
public class SecurityConfigurerAdapterClosureTests {
|
||||
|
||||
ConcereteSecurityConfigurerAdapter conf = new ConcereteSecurityConfigurerAdapter();
|
||||
|
||||
@Test
|
||||
@@ -49,8 +49,8 @@ public class SecurityConfigurerAdapterClosureTests {
|
||||
assertThat(this.conf.list).contains("a");
|
||||
}
|
||||
|
||||
static class ConcereteSecurityConfigurerAdapter extends
|
||||
SecurityConfigurerAdapter<Object, SecurityBuilder<Object>> {
|
||||
static class ConcereteSecurityConfigurerAdapter extends SecurityConfigurerAdapter<Object, SecurityBuilder<Object>> {
|
||||
|
||||
private List<Object> list = new ArrayList<Object>();
|
||||
|
||||
@Override
|
||||
@@ -62,5 +62,7 @@ public class SecurityConfigurerAdapterClosureTests {
|
||||
this.list = l;
|
||||
return this;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -22,6 +22,7 @@ import org.junit.Test;
|
||||
import org.springframework.core.Ordered;
|
||||
|
||||
public class SecurityConfigurerAdapterTests {
|
||||
|
||||
ConcereteSecurityConfigurerAdapter adapter;
|
||||
|
||||
@Before
|
||||
@@ -39,6 +40,7 @@ public class SecurityConfigurerAdapterTests {
|
||||
}
|
||||
|
||||
static class OrderedObjectPostProcessor implements ObjectPostProcessor<String>, Ordered {
|
||||
|
||||
private final int order;
|
||||
|
||||
OrderedObjectPostProcessor(int order) {
|
||||
@@ -53,5 +55,7 @@ public class SecurityConfigurerAdapterTests {
|
||||
public String postProcess(String object) {
|
||||
return object + " " + order;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -63,6 +63,7 @@ import static org.springframework.security.test.web.servlet.response.SecurityMoc
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class AuthenticationManagerBuilderTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -84,15 +85,14 @@ public class AuthenticationManagerBuilderTests {
|
||||
ObjectPostProcessor<Object> opp = mock(ObjectPostProcessor.class);
|
||||
AuthenticationEventPublisher aep = mock(AuthenticationEventPublisher.class);
|
||||
when(opp.postProcess(any())).thenAnswer(a -> a.getArgument(0));
|
||||
AuthenticationManager am = new AuthenticationManagerBuilder(opp)
|
||||
.authenticationEventPublisher(aep)
|
||||
.inMemoryAuthentication()
|
||||
.and()
|
||||
.build();
|
||||
AuthenticationManager am = new AuthenticationManagerBuilder(opp).authenticationEventPublisher(aep)
|
||||
.inMemoryAuthentication().and().build();
|
||||
|
||||
try {
|
||||
am.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
} catch (AuthenticationException success) {}
|
||||
}
|
||||
catch (AuthenticationException success) {
|
||||
}
|
||||
|
||||
verify(aep).publishAuthenticationFailure(any(), any());
|
||||
}
|
||||
@@ -100,8 +100,8 @@ public class AuthenticationManagerBuilderTests {
|
||||
@Test
|
||||
public void getAuthenticationManagerWhenGlobalPasswordEncoderBeanThenUsed() throws Exception {
|
||||
this.spring.register(PasswordEncoderGlobalConfig.class).autowire();
|
||||
AuthenticationManager manager = this.spring.getContext()
|
||||
.getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager manager = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
|
||||
Authentication auth = manager.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
|
||||
@@ -111,6 +111,7 @@ public class AuthenticationManagerBuilderTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderGlobalConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -124,13 +125,14 @@ public class AuthenticationManagerBuilderTests {
|
||||
PasswordEncoder passwordEncoder() {
|
||||
return NoOpPasswordEncoder.getInstance();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationManagerWhenProtectedPasswordEncoderBeanThenUsed() throws Exception {
|
||||
this.spring.register(PasswordEncoderGlobalConfig.class).autowire();
|
||||
AuthenticationManager manager = this.spring.getContext()
|
||||
.getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager manager = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
|
||||
Authentication auth = manager.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
|
||||
@@ -140,6 +142,7 @@ public class AuthenticationManagerBuilderTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
auth
|
||||
@@ -152,6 +155,7 @@ public class AuthenticationManagerBuilderTests {
|
||||
PasswordEncoder passwordEncoder() {
|
||||
return NoOpPasswordEncoder.getInstance();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Autowired(required = false)
|
||||
@@ -161,22 +165,18 @@ public class AuthenticationManagerBuilderTests {
|
||||
public void authenticationManagerWhenMultipleProvidersThenWorks() throws Exception {
|
||||
this.spring.register(MultiAuthenticationProvidersConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withUsername("user").withRoles("USER"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated().withUsername("user").withRoles("USER"));
|
||||
|
||||
this.mockMvc.perform(formLogin().user("admin"))
|
||||
.andExpect(authenticated().withUsername("admin").withRoles("USER", "ADMIN"));
|
||||
.andExpect(authenticated().withUsername("admin").withRoles("USER", "ADMIN"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class MultiAuthenticationProvidersConfig
|
||||
extends WebSecurityConfigurerAdapter {
|
||||
static class MultiAuthenticationProvidersConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication()
|
||||
.withUser(PasswordEncodedUser.user())
|
||||
.and()
|
||||
.inMemoryAuthentication()
|
||||
.withUser(PasswordEncodedUser.admin());
|
||||
auth.inMemoryAuthentication().withUser(PasswordEncodedUser.user()).and().inMemoryAuthentication()
|
||||
.withUser(PasswordEncodedUser.admin());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -219,7 +219,7 @@ public class AuthenticationManagerBuilderTests {
|
||||
this.spring.register(UserFromPropertiesConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("joe", "joespassword"))
|
||||
.andExpect(authenticated().withUsername("joe").withRoles("USER"));
|
||||
.andExpect(authenticated().withUsername("joe").withRoles("USER"));
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@@ -248,6 +248,7 @@ public class AuthenticationManagerBuilderTests {
|
||||
properties.load(this.users.getInputStream());
|
||||
return new InMemoryUserDetailsManager(properties);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -19,13 +19,12 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
@Configuration
|
||||
public class BaseAuthenticationConfig {
|
||||
|
||||
@Autowired
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -35,4 +34,5 @@ public class BaseAuthenticationConfig {
|
||||
.withUser("admin").password("password").roles("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -33,6 +33,7 @@ import static org.springframework.security.test.web.servlet.response.SecurityMoc
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class NamespaceAuthenticationManagerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -44,15 +45,16 @@ public class NamespaceAuthenticationManagerTests {
|
||||
this.spring.register(EraseCredentialsTrueDefaultConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(a-> assertThat(a.getCredentials()).isNull()));
|
||||
.andExpect(authenticated().withAuthentication(a -> assertThat(a.getCredentials()).isNull()));
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(a-> assertThat(a.getCredentials()).isNull()));
|
||||
.andExpect(authenticated().withAuthentication(a -> assertThat(a.getCredentials()).isNull()));
|
||||
// no exception due to username being cleared out
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EraseCredentialsTrueDefaultConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -61,6 +63,7 @@ public class NamespaceAuthenticationManagerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -68,15 +71,16 @@ public class NamespaceAuthenticationManagerTests {
|
||||
this.spring.register(EraseCredentialsFalseConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(a-> assertThat(a.getCredentials()).isNotNull()));
|
||||
.andExpect(authenticated().withAuthentication(a -> assertThat(a.getCredentials()).isNotNull()));
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(a-> assertThat(a.getCredentials()).isNotNull()));
|
||||
.andExpect(authenticated().withAuthentication(a -> assertThat(a.getCredentials()).isNotNull()));
|
||||
// no exception due to username being cleared out
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EraseCredentialsFalseConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -86,6 +90,7 @@ public class NamespaceAuthenticationManagerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -94,11 +99,12 @@ public class NamespaceAuthenticationManagerTests {
|
||||
this.spring.register(GlobalEraseCredentialsFalseConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(a-> assertThat(a.getCredentials()).isNotNull()));
|
||||
.andExpect(authenticated().withAuthentication(a -> assertThat(a.getCredentials()).isNotNull()));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class GlobalEraseCredentialsFalseConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -108,5 +114,7 @@ public class NamespaceAuthenticationManagerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -49,12 +49,12 @@ public class NamespaceAuthenticationProviderTests {
|
||||
public void authenticationProviderRef() throws Exception {
|
||||
this.spring.register(AuthenticationProviderRefConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthenticationProviderRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) {
|
||||
// @formatter:off
|
||||
auth
|
||||
@@ -68,6 +68,7 @@ public class NamespaceAuthenticationProviderTests {
|
||||
result.setUserDetailsService(new InMemoryUserDetailsManager(PasswordEncodedUser.user()));
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -75,12 +76,12 @@ public class NamespaceAuthenticationProviderTests {
|
||||
public void authenticationProviderUserServiceRef() throws Exception {
|
||||
this.spring.register(AuthenticationProviderRefConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class UserServiceRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
auth
|
||||
@@ -92,5 +93,7 @@ public class NamespaceAuthenticationProviderTests {
|
||||
public UserDetailsService userDetailsService() {
|
||||
return new InMemoryUserDetailsManager(PasswordEncodedUser.user());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -53,12 +53,12 @@ public class NamespaceJdbcUserServiceTests {
|
||||
public void jdbcUserService() throws Exception {
|
||||
this.spring.register(DataSourceConfig.class, JdbcUserServiceConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class JdbcUserServiceConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
private DataSource dataSource;
|
||||
|
||||
@@ -71,27 +71,30 @@ public class NamespaceJdbcUserServiceTests {
|
||||
.dataSource(this.dataSource); // jdbc-user-service@data-source-ref
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class DataSourceConfig {
|
||||
|
||||
@Bean
|
||||
public DataSource dataSource() {
|
||||
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
|
||||
return builder.setType(EmbeddedDatabaseType.HSQL).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void jdbcUserServiceCustom() throws Exception {
|
||||
this.spring.register(CustomDataSourceConfig.class, CustomJdbcUserServiceSampleConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withUsername("user").withRoles("DBA", "USER"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated().withUsername("user").withRoles("DBA", "USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomJdbcUserServiceSampleConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
private DataSource dataSource;
|
||||
|
||||
@@ -129,16 +132,22 @@ public class NamespaceJdbcUserServiceTests {
|
||||
@Override
|
||||
public void removeUserFromCache(String username) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class CustomDataSourceConfig {
|
||||
|
||||
@Bean
|
||||
public DataSource dataSource() {
|
||||
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder()
|
||||
// simulate that the DB already has the schema loaded and users in it
|
||||
.addScript("CustomJdbcUserServiceSampleConfig.sql");
|
||||
// simulate that the DB already has the schema loaded and users in it
|
||||
.addScript("CustomJdbcUserServiceSampleConfig.sql");
|
||||
return builder.setType(EmbeddedDatabaseType.HSQL).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -52,12 +52,12 @@ public class NamespacePasswordEncoderTests {
|
||||
public void passwordEncoderRefWithInMemory() throws Exception {
|
||||
this.spring.register(PasswordEncoderWithInMemoryConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderWithInMemoryConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
BCryptPasswordEncoder encoder = new BCryptPasswordEncoder();
|
||||
@@ -68,18 +68,19 @@ public class NamespacePasswordEncoderTests {
|
||||
.passwordEncoder(encoder);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void passwordEncoderRefWithJdbc() throws Exception {
|
||||
this.spring.register(PasswordEncoderWithJdbcConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderWithJdbcConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
|
||||
@@ -99,18 +100,19 @@ public class NamespacePasswordEncoderTests {
|
||||
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
|
||||
return builder.setType(EmbeddedDatabaseType.HSQL).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void passwordEncoderRefWithUserDetailsService() throws Exception {
|
||||
this.spring.register(PasswordEncoderWithUserDetailsServiceConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderWithUserDetailsServiceConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
BCryptPasswordEncoder encoder = new BCryptPasswordEncoder();
|
||||
@@ -134,5 +136,7 @@ public class NamespacePasswordEncoderTests {
|
||||
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
|
||||
return builder.setType(EmbeddedDatabaseType.HSQL).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -49,6 +49,7 @@ public class PasswordEncoderConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
BCryptPasswordEncoder encoder = passwordEncoder();
|
||||
// @formatter:off
|
||||
@@ -67,19 +68,19 @@ public class PasswordEncoderConfigurerTests {
|
||||
public BCryptPasswordEncoder passwordEncoder() {
|
||||
return new BCryptPasswordEncoder();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void passwordEncoderRefWhenAuthenticationManagerBuilderThenAuthenticationSuccess() throws Exception {
|
||||
this.spring.register(PasswordEncoderNoAuthManagerLoadsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PasswordEncoderNoAuthManagerLoadsConfig extends
|
||||
WebSecurityConfigurerAdapter {
|
||||
static class PasswordEncoderNoAuthManagerLoadsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
BCryptPasswordEncoder encoder = passwordEncoder();
|
||||
// @formatter:off
|
||||
@@ -94,5 +95,7 @@ public class PasswordEncoderConfigurerTests {
|
||||
public BCryptPasswordEncoder passwordEncoder() {
|
||||
return new BCryptPasswordEncoder();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -37,6 +37,7 @@ import static org.assertj.core.api.Assertions.*;
|
||||
*/
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
public class AuthenticationConfigurationPublishTests {
|
||||
|
||||
@Autowired
|
||||
MockEventListener<AuthenticationSuccessEvent> listener;
|
||||
|
||||
@@ -58,6 +59,7 @@ public class AuthenticationConfigurationPublishTests {
|
||||
@EnableGlobalAuthentication
|
||||
@Import(AuthenticationTestConfiguration.class)
|
||||
static class Config {
|
||||
|
||||
@Bean
|
||||
AuthenticationEventPublisher publisher() {
|
||||
return new DefaultAuthenticationEventPublisher();
|
||||
@@ -65,8 +67,10 @@ public class AuthenticationConfigurationPublishTests {
|
||||
|
||||
@Bean
|
||||
MockEventListener<AuthenticationSuccessEvent> eventListener() {
|
||||
return new MockEventListener<AuthenticationSuccessEvent>(){};
|
||||
return new MockEventListener<AuthenticationSuccessEvent>() {
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -79,81 +79,100 @@ public class AuthenticationConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void orderingAutowiredOnEnableGlobalMethodSecurity() {
|
||||
this.spring.register(AuthenticationTestConfiguration.class, GlobalMethodSecurityAutowiredConfig.class, ServicesConfig.class).autowire();
|
||||
this.spring.register(AuthenticationTestConfiguration.class, GlobalMethodSecurityAutowiredConfig.class,
|
||||
ServicesConfig.class).autowire();
|
||||
|
||||
SecurityContextHolder.getContext().setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
SecurityContextHolder.getContext()
|
||||
.setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
this.service.run();
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(securedEnabled = true)
|
||||
static class GlobalMethodSecurityAutowiredConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void orderingAutowiredOnEnableWebSecurity() {
|
||||
this.spring.register(AuthenticationTestConfiguration.class, WebSecurityConfig.class, GlobalMethodSecurityAutowiredConfig.class, ServicesConfig.class).autowire();
|
||||
this.spring.register(AuthenticationTestConfiguration.class, WebSecurityConfig.class,
|
||||
GlobalMethodSecurityAutowiredConfig.class, ServicesConfig.class).autowire();
|
||||
|
||||
SecurityContextHolder.getContext().setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
SecurityContextHolder.getContext()
|
||||
.setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
this.service.run();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityConfig {}
|
||||
static class WebSecurityConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void orderingAutowiredOnEnableWebMvcSecurity() {
|
||||
this.spring.register(AuthenticationTestConfiguration.class, WebMvcSecurityConfig.class, GlobalMethodSecurityAutowiredConfig.class, ServicesConfig.class).autowire();
|
||||
this.spring.register(AuthenticationTestConfiguration.class, WebMvcSecurityConfig.class,
|
||||
GlobalMethodSecurityAutowiredConfig.class, ServicesConfig.class).autowire();
|
||||
|
||||
SecurityContextHolder.getContext().setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
SecurityContextHolder.getContext()
|
||||
.setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
this.service.run();
|
||||
}
|
||||
|
||||
@EnableWebMvcSecurity
|
||||
static class WebMvcSecurityConfig {}
|
||||
static class WebMvcSecurityConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationManagerWhenNoAuthenticationThenNull() throws Exception {
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager()).isNull();
|
||||
assertThat(this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager())
|
||||
.isNull();
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void getAuthenticationManagerWhenNoOpGlobalAuthenticationConfigurerAdapterThenNull() throws Exception {
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class, NoOpGlobalAuthenticationConfigurerAdapter.class).autowire();
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class,
|
||||
NoOpGlobalAuthenticationConfigurerAdapter.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager()).isNull();
|
||||
assertThat(this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager())
|
||||
.isNull();
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class NoOpGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {}
|
||||
static class NoOpGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenGlobalAuthenticationConfigurerAdapterThenAuthenticates() throws Exception {
|
||||
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken("user", "password");
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class, UserGlobalAuthenticationConfigurerAdapter.class).autowire();
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class,
|
||||
UserGlobalAuthenticationConfigurerAdapter.class).autowire();
|
||||
|
||||
AuthenticationManager authentication = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager authentication = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
|
||||
assertThat(authentication.authenticate(token).getName()).isEqualTo(token.getName());
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class UserGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication()
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
auth.inMemoryAuthentication().withUser(PasswordEncodedUser.user());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenAuthenticationManagerBeanThenAuthenticates() throws Exception {
|
||||
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken("user", "password");
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class, AuthenticationManagerBeanConfig.class).autowire();
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class,
|
||||
AuthenticationManagerBeanConfig.class).autowire();
|
||||
|
||||
AuthenticationManager authentication = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager authentication = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(authentication.authenticate(token)).thenReturn(TestAuthentication.authenticatedUser());
|
||||
|
||||
assertThat(authentication.authenticate(token).getName()).isEqualTo(token.getName());
|
||||
@@ -161,70 +180,93 @@ public class AuthenticationConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
static class AuthenticationManagerBeanConfig {
|
||||
|
||||
AuthenticationManager authenticationManager = mock(AuthenticationManager.class);
|
||||
|
||||
@Bean
|
||||
public AuthenticationManager authenticationManager() {
|
||||
return this.authenticationManager;
|
||||
}
|
||||
|
||||
}
|
||||
//
|
||||
// //
|
||||
//
|
||||
@Configuration
|
||||
static class ServicesConfig {
|
||||
@Bean
|
||||
public Service service() {
|
||||
return new ServiceImpl();
|
||||
}
|
||||
|
||||
//
|
||||
// //
|
||||
//
|
||||
@Configuration
|
||||
static class ServicesConfig {
|
||||
|
||||
@Bean
|
||||
public Service service() {
|
||||
return new ServiceImpl();
|
||||
}
|
||||
|
||||
interface Service {
|
||||
void run();
|
||||
}
|
||||
|
||||
interface Service {
|
||||
|
||||
void run();
|
||||
|
||||
}
|
||||
|
||||
static class ServiceImpl implements Service {
|
||||
|
||||
@Secured("ROLE_USER")
|
||||
public void run() {
|
||||
}
|
||||
|
||||
static class ServiceImpl implements Service {
|
||||
@Secured("ROLE_USER")
|
||||
public void run() {}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenMultipleThenOrdered() throws Exception {
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class,
|
||||
AuthenticationManagerBeanConfig.class).autowire();
|
||||
AuthenticationConfiguration config = this.spring.getContext().getBean(AuthenticationConfiguration.class);
|
||||
config.setGlobalAuthenticationConfigurers(Arrays.asList(new LowestOrderGlobalAuthenticationConfigurerAdapter(),
|
||||
new HighestOrderGlobalAuthenticationConfigurerAdapter(),
|
||||
new DefaultOrderGlobalAuthenticationConfigurerAdapter()));
|
||||
}
|
||||
|
||||
static class DefaultOrderGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
static List<Class<?>> inits = new ArrayList<>();
|
||||
static List<Class<?>> configs = new ArrayList<>();
|
||||
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
inits.add(getClass());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenMultipleThenOrdered() throws Exception {
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class, AuthenticationManagerBeanConfig.class).autowire();
|
||||
AuthenticationConfiguration config = this.spring.getContext().getBean(AuthenticationConfiguration.class);
|
||||
config.setGlobalAuthenticationConfigurers(Arrays.asList(new LowestOrderGlobalAuthenticationConfigurerAdapter(), new HighestOrderGlobalAuthenticationConfigurerAdapter(), new DefaultOrderGlobalAuthenticationConfigurerAdapter()));
|
||||
public void configure(AuthenticationManagerBuilder auth) {
|
||||
configs.add(getClass());
|
||||
}
|
||||
|
||||
static class DefaultOrderGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {
|
||||
static List<Class<?>> inits = new ArrayList<>();
|
||||
static List<Class<?>> configs = new ArrayList<>();
|
||||
}
|
||||
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
inits.add(getClass());
|
||||
}
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
static class LowestOrderGlobalAuthenticationConfigurerAdapter
|
||||
extends DefaultOrderGlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
public void configure(AuthenticationManagerBuilder auth) {
|
||||
configs.add(getClass());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
static class LowestOrderGlobalAuthenticationConfigurerAdapter extends DefaultOrderGlobalAuthenticationConfigurerAdapter {}
|
||||
@Order(Ordered.HIGHEST_PRECEDENCE)
|
||||
static class HighestOrderGlobalAuthenticationConfigurerAdapter
|
||||
extends DefaultOrderGlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
@Order(Ordered.HIGHEST_PRECEDENCE)
|
||||
static class HighestOrderGlobalAuthenticationConfigurerAdapter extends DefaultOrderGlobalAuthenticationConfigurerAdapter {}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenConfiguredThenBootNotTrigger() throws Exception {
|
||||
this.spring.register(AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class).autowire();
|
||||
AuthenticationConfiguration config = this.spring.getContext().getBean(AuthenticationConfiguration.class);
|
||||
config.setGlobalAuthenticationConfigurers(Arrays.asList(new ConfiguresInMemoryConfigurerAdapter(), new BootGlobalAuthenticationConfigurerAdapter()));
|
||||
config.setGlobalAuthenticationConfigurers(Arrays.asList(new ConfiguresInMemoryConfigurerAdapter(),
|
||||
new BootGlobalAuthenticationConfigurerAdapter()));
|
||||
AuthenticationManager authenticationManager = config.getAuthenticationManager();
|
||||
|
||||
authenticationManager.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
|
||||
assertThatThrownBy(() -> authenticationManager.authenticate(new UsernamePasswordAuthenticationToken("boot", "password")))
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
assertThatThrownBy(
|
||||
() -> authenticationManager.authenticate(new UsernamePasswordAuthenticationToken("boot", "password")))
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
|
||||
}
|
||||
|
||||
@@ -247,16 +289,21 @@ public class AuthenticationConfigurationTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
static class BootGlobalAuthenticationConfigurerAdapter extends DefaultOrderGlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.apply(new DefaultBootGlobalAuthenticationConfigurerAdapter());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class DefaultBootGlobalAuthenticationConfigurerAdapter extends DefaultOrderGlobalAuthenticationConfigurerAdapter {
|
||||
static class DefaultBootGlobalAuthenticationConfigurerAdapter
|
||||
extends DefaultOrderGlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(AuthenticationManagerBuilder auth) {
|
||||
if (auth.isConfigured()) {
|
||||
@@ -273,6 +320,7 @@ public class AuthenticationConfigurationTests {
|
||||
|
||||
auth.authenticationProvider(provider);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-2531
|
||||
@@ -301,6 +349,7 @@ public class AuthenticationConfigurationTests {
|
||||
public AuthenticationManager manager() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -313,19 +362,24 @@ public class AuthenticationConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
@Import(AuthenticationConfiguration.class)
|
||||
static class Sec2822Config {}
|
||||
static class Sec2822Config {
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@EnableWebSecurity
|
||||
static class Sec2822WebSecurity extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class Sec2822UseAuth {
|
||||
|
||||
@Autowired
|
||||
public void useAuthenticationManager(AuthenticationConfiguration auth) throws Exception {
|
||||
auth.getAuthenticationManager();
|
||||
@@ -338,52 +392,62 @@ public class AuthenticationConfigurationTests {
|
||||
return new BootGlobalAuthenticationConfigurerAdapter();
|
||||
}
|
||||
|
||||
static class BootGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter { }
|
||||
static class BootGlobalAuthenticationConfigurerAdapter extends GlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// sec-2868
|
||||
@Test
|
||||
public void getAuthenticationWhenUserDetailsServiceBeanThenAuthenticationManagerUsesUserDetailsServiceBean() throws Exception {
|
||||
public void getAuthenticationWhenUserDetailsServiceBeanThenAuthenticationManagerUsesUserDetailsServiceBean()
|
||||
throws Exception {
|
||||
this.spring.register(UserDetailsServiceBeanConfig.class).autowire();
|
||||
UserDetailsService uds = this.spring.getContext().getBean(UserDetailsService.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(uds.loadUserByUsername("user")).thenReturn(PasswordEncodedUser.user(), PasswordEncodedUser.user());
|
||||
|
||||
am.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
|
||||
assertThatThrownBy(() -> am.authenticate(new UsernamePasswordAuthenticationToken("user", "invalid")))
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import({AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class})
|
||||
@Import({ AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class })
|
||||
static class UserDetailsServiceBeanConfig {
|
||||
|
||||
UserDetailsService uds = mock(UserDetailsService.class);
|
||||
|
||||
@Bean
|
||||
UserDetailsService userDetailsService() {
|
||||
return this.uds;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenUserDetailsServiceAndPasswordEncoderBeanThenEncoderUsed() throws Exception {
|
||||
UserDetails user = new User("user", "$2a$10$FBAKClV1zBIOOC9XMXf3AO8RoGXYVYsfvUdoLxGkd/BnXEn4tqT3u",
|
||||
AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
this.spring.register(UserDetailsServiceBeanWithPasswordEncoderConfig.class).autowire();
|
||||
UserDetailsService uds = this.spring.getContext().getBean(UserDetailsService.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
when(uds.loadUserByUsername("user")).thenReturn(User.withUserDetails(user).build(), User.withUserDetails(user).build());
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(uds.loadUserByUsername("user")).thenReturn(User.withUserDetails(user).build(),
|
||||
User.withUserDetails(user).build());
|
||||
|
||||
am.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
|
||||
assertThatThrownBy(() -> am.authenticate(new UsernamePasswordAuthenticationToken("user", "invalid")))
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
.isInstanceOf(AuthenticationException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import({AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class})
|
||||
@Import({ AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class })
|
||||
static class UserDetailsServiceBeanWithPasswordEncoderConfig {
|
||||
|
||||
UserDetailsService uds = mock(UserDetailsService.class);
|
||||
|
||||
@Bean
|
||||
@@ -395,16 +459,19 @@ public class AuthenticationConfigurationTests {
|
||||
PasswordEncoder passwordEncoder() {
|
||||
return new BCryptPasswordEncoder();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenUserDetailsServiceAndPasswordManagerThenManagerUsed() throws Exception {
|
||||
UserDetails user = new User("user", "{noop}password",
|
||||
AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
UserDetails user = new User("user", "{noop}password", AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
this.spring.register(UserDetailsPasswordManagerBeanConfig.class).autowire();
|
||||
UserDetailsPasswordManagerBeanConfig.Manager manager = this.spring.getContext().getBean(UserDetailsPasswordManagerBeanConfig.Manager.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
when(manager.loadUserByUsername("user")).thenReturn(User.withUserDetails(user).build(), User.withUserDetails(user).build());
|
||||
UserDetailsPasswordManagerBeanConfig.Manager manager = this.spring.getContext()
|
||||
.getBean(UserDetailsPasswordManagerBeanConfig.Manager.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(manager.loadUserByUsername("user")).thenReturn(User.withUserDetails(user).build(),
|
||||
User.withUserDetails(user).build());
|
||||
when(manager.updatePassword(any(), any())).thenReturn(user);
|
||||
|
||||
am.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
@@ -413,8 +480,9 @@ public class AuthenticationConfigurationTests {
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import({AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class})
|
||||
@Import({ AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class })
|
||||
static class UserDetailsPasswordManagerBeanConfig {
|
||||
|
||||
Manager manager = mock(Manager.class);
|
||||
|
||||
@Bean
|
||||
@@ -423,15 +491,18 @@ public class AuthenticationConfigurationTests {
|
||||
}
|
||||
|
||||
interface Manager extends UserDetailsService, UserDetailsPasswordService {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//gh-3091
|
||||
// gh-3091
|
||||
@Test
|
||||
public void getAuthenticationWhenAuthenticationProviderBeanThenUsed() throws Exception {
|
||||
this.spring.register(AuthenticationProviderBeanConfig.class).autowire();
|
||||
AuthenticationProvider ap = this.spring.getContext().getBean(AuthenticationProvider.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(ap.supports(any())).thenReturn(true);
|
||||
when(ap.authenticate(any())).thenReturn(TestAuthentication.authenticatedUser());
|
||||
|
||||
@@ -439,21 +510,25 @@ public class AuthenticationConfigurationTests {
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import({AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class})
|
||||
@Import({ AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class })
|
||||
static class AuthenticationProviderBeanConfig {
|
||||
|
||||
AuthenticationProvider provider = mock(AuthenticationProvider.class);
|
||||
|
||||
@Bean
|
||||
AuthenticationProvider authenticationProvider() {
|
||||
return this.provider;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAuthenticationWhenAuthenticationProviderAndUserDetailsBeanThenAuthenticationProviderUsed() throws Exception {
|
||||
public void getAuthenticationWhenAuthenticationProviderAndUserDetailsBeanThenAuthenticationProviderUsed()
|
||||
throws Exception {
|
||||
this.spring.register(AuthenticationProviderBeanAndUserDetailsServiceConfig.class).autowire();
|
||||
AuthenticationProvider ap = this.spring.getContext().getBean(AuthenticationProvider.class);
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
AuthenticationManager am = this.spring.getContext().getBean(AuthenticationConfiguration.class)
|
||||
.getAuthenticationManager();
|
||||
when(ap.supports(any())).thenReturn(true);
|
||||
when(ap.authenticate(any())).thenReturn(TestAuthentication.authenticatedUser());
|
||||
|
||||
@@ -461,8 +536,9 @@ public class AuthenticationConfigurationTests {
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import({AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class})
|
||||
@Import({ AuthenticationConfiguration.class, ObjectPostProcessorConfiguration.class })
|
||||
static class AuthenticationProviderBeanAndUserDetailsServiceConfig {
|
||||
|
||||
AuthenticationProvider provider = mock(AuthenticationProvider.class);
|
||||
|
||||
UserDetailsService uds = mock(UserDetailsService.class);
|
||||
@@ -476,11 +552,13 @@ public class AuthenticationConfigurationTests {
|
||||
AuthenticationProvider authenticationProvider() {
|
||||
return this.provider;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void enableGlobalMethodSecurityWhenPreAuthorizeThenNoException() {
|
||||
this.spring.register(UsesPreAuthorizeMethodSecurityConfig.class, AuthenticationManagerBeanConfig.class).autowire();
|
||||
this.spring.register(UsesPreAuthorizeMethodSecurityConfig.class, AuthenticationManagerBeanConfig.class)
|
||||
.autowire();
|
||||
|
||||
// no exception
|
||||
}
|
||||
@@ -488,13 +566,17 @@ public class AuthenticationConfigurationTests {
|
||||
@Configuration
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
static class UsesPreAuthorizeMethodSecurityConfig {
|
||||
|
||||
@PreAuthorize("denyAll")
|
||||
void run() {}
|
||||
void run() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void enableGlobalMethodSecurityWhenPreAuthorizeThenUsesMethodSecurityService() {
|
||||
this.spring.register(ServicesConfig.class, UsesPreAuthorizeMethodSecurityConfig.class, AuthenticationManagerBeanConfig.class).autowire();
|
||||
this.spring.register(ServicesConfig.class, UsesPreAuthorizeMethodSecurityConfig.class,
|
||||
AuthenticationManagerBeanConfig.class).autowire();
|
||||
|
||||
// no exception
|
||||
}
|
||||
@@ -502,8 +584,10 @@ public class AuthenticationConfigurationTests {
|
||||
@Configuration
|
||||
@EnableGlobalMethodSecurity(securedEnabled = true)
|
||||
static class UsesServiceMethodSecurityConfig {
|
||||
|
||||
@Autowired
|
||||
Service service;
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -537,11 +621,12 @@ public class AuthenticationConfigurationTests {
|
||||
|
||||
this.spring.getContext().getBean(AuthenticationConfiguration.class).getAuthenticationManager();
|
||||
|
||||
assertThatThrownBy(ap::build)
|
||||
.isInstanceOf(AlreadyBuiltException.class);
|
||||
assertThatThrownBy(ap::build).isInstanceOf(AlreadyBuiltException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class AuthenticationConfigurationSubclass extends AuthenticationConfiguration {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -26,11 +26,11 @@ import org.springframework.security.config.annotation.authentication.builders.Au
|
||||
import org.springframework.security.config.test.SpringTestRule;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*
|
||||
*/
|
||||
public class EnableGlobalAuthenticationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -52,6 +52,7 @@ public class EnableGlobalAuthenticationTests {
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication().withUser("user").password("password").roles("USER");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -66,6 +67,7 @@ public class EnableGlobalAuthenticationTests {
|
||||
|
||||
@EnableGlobalAuthentication
|
||||
static class BeanProxyEnabledByDefaultConfig {
|
||||
|
||||
@Bean
|
||||
public Child child() {
|
||||
return new Child();
|
||||
@@ -75,6 +77,7 @@ public class EnableGlobalAuthenticationTests {
|
||||
public Parent parent() {
|
||||
return new Parent(child());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -90,6 +93,7 @@ public class EnableGlobalAuthenticationTests {
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableGlobalAuthentication
|
||||
static class BeanProxyDisabledConfig {
|
||||
|
||||
@Bean
|
||||
public Child child() {
|
||||
return new Child();
|
||||
@@ -99,9 +103,11 @@ public class EnableGlobalAuthenticationTests {
|
||||
public Parent parent() {
|
||||
return new Parent(child());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class Parent {
|
||||
|
||||
private Child child;
|
||||
|
||||
Parent(Child child) {
|
||||
@@ -111,10 +117,14 @@ public class EnableGlobalAuthenticationTests {
|
||||
public Child getChild() {
|
||||
return child;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class Child {
|
||||
|
||||
Child() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -41,4 +41,5 @@ public class LdapAuthenticationProviderConfigurerTests {
|
||||
assertThat(configurer.getAuthoritiesMapper()).isInstanceOf(NullAuthoritiesMapper.class);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -28,10 +28,9 @@ import org.springframework.security.core.userdetails.UserDetails;
|
||||
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @author Adolfo Eloy
|
||||
*/
|
||||
* @author Rob Winch
|
||||
* @author Adolfo Eloy
|
||||
*/
|
||||
public class UserDetailsManagerConfigurerTests {
|
||||
|
||||
private InMemoryUserDetailsManager userDetailsManager;
|
||||
@@ -43,16 +42,9 @@ public class UserDetailsManagerConfigurerTests {
|
||||
|
||||
@Test
|
||||
public void allAttributesSupported() {
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder,
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(userDetailsManager)
|
||||
.withUser("user")
|
||||
.password("password")
|
||||
.roles("USER")
|
||||
.disabled(true)
|
||||
.accountExpired(true)
|
||||
.accountLocked(true)
|
||||
.credentialsExpired(true)
|
||||
.build();
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder, InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(
|
||||
userDetailsManager).withUser("user").password("password").roles("USER").disabled(true)
|
||||
.accountExpired(true).accountLocked(true).credentialsExpired(true).build();
|
||||
|
||||
assertThat(userDetails.getUsername()).isEqualTo("user");
|
||||
assertThat(userDetails.getPassword()).isEqualTo("password");
|
||||
@@ -67,12 +59,8 @@ public class UserDetailsManagerConfigurerTests {
|
||||
public void authoritiesWithGrantedAuthorityWorks() {
|
||||
SimpleGrantedAuthority authority = new SimpleGrantedAuthority("ROLE_USER");
|
||||
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder,
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(userDetailsManager)
|
||||
.withUser("user")
|
||||
.password("password")
|
||||
.authorities(authority)
|
||||
.build();
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder, InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(
|
||||
userDetailsManager).withUser("user").password("password").authorities(authority).build();
|
||||
|
||||
assertThat(userDetails.getAuthorities().stream().findFirst().get()).isEqualTo(authority);
|
||||
}
|
||||
@@ -81,12 +69,8 @@ public class UserDetailsManagerConfigurerTests {
|
||||
public void authoritiesWithStringAuthorityWorks() {
|
||||
String authority = "ROLE_USER";
|
||||
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder,
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(userDetailsManager)
|
||||
.withUser("user")
|
||||
.password("password")
|
||||
.authorities(authority)
|
||||
.build();
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder, InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(
|
||||
userDetailsManager).withUser("user").password("password").authorities(authority).build();
|
||||
|
||||
assertThat(userDetails.getAuthorities().stream().findFirst().get().getAuthority()).isEqualTo(authority);
|
||||
}
|
||||
@@ -95,13 +79,10 @@ public class UserDetailsManagerConfigurerTests {
|
||||
public void authoritiesWithAListOfGrantedAuthorityWorks() {
|
||||
SimpleGrantedAuthority authority = new SimpleGrantedAuthority("ROLE_USER");
|
||||
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder,
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(userDetailsManager)
|
||||
.withUser("user")
|
||||
.password("password")
|
||||
.authorities(Arrays.asList(authority))
|
||||
.build();
|
||||
UserDetails userDetails = new UserDetailsManagerConfigurer<AuthenticationManagerBuilder, InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder>>(
|
||||
userDetailsManager).withUser("user").password("password").authorities(Arrays.asList(authority)).build();
|
||||
|
||||
assertThat(userDetails.getAuthorities().stream().findFirst().get()).isEqualTo(authority);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -19,7 +19,9 @@ import org.aopalliance.intercept.MethodInterceptor;
|
||||
import org.aopalliance.intercept.MethodInvocation;
|
||||
|
||||
public class AroundMethodInterceptor implements MethodInterceptor {
|
||||
|
||||
public Object invoke(MethodInvocation methodInvocation) throws Throwable {
|
||||
return String.valueOf(methodInvocation.proceed());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -39,10 +39,10 @@ import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.verify;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class AutowireBeanFactoryObjectPostProcessorTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -127,10 +127,12 @@ public class AutowireBeanFactoryObjectPostProcessorTests {
|
||||
|
||||
@Configuration
|
||||
static class Config {
|
||||
|
||||
@Bean
|
||||
public ObjectPostProcessor objectPostProcessor(AutowireCapableBeanFactory beanFactory) {
|
||||
return new AutowireBeanFactoryObjectPostProcessor(beanFactory);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -144,12 +146,14 @@ public class AutowireBeanFactoryObjectPostProcessorTests {
|
||||
|
||||
@Configuration
|
||||
static class SmartConfig {
|
||||
|
||||
SmartInitializingSingleton toTest = mock(SmartInitializingSingleton.class);
|
||||
|
||||
@Autowired
|
||||
public void configure(ObjectPostProcessor<Object> p) {
|
||||
p.postProcess(this.toTest);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -164,6 +168,7 @@ public class AutowireBeanFactoryObjectPostProcessorTests {
|
||||
|
||||
@Configuration
|
||||
static class WithBeanNameAutoProxyCreatorConfig {
|
||||
|
||||
@Bean
|
||||
public ObjectPostProcessor objectPostProcessor(AutowireCapableBeanFactory beanFactory) {
|
||||
return new AutowireBeanFactoryObjectPostProcessor(beanFactory);
|
||||
@@ -173,5 +178,7 @@ public class AutowireBeanFactoryObjectPostProcessorTests {
|
||||
public void configure(ObjectPostProcessor<Object> p) {
|
||||
p.postProcess(new Object());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -20,4 +20,5 @@ public class MyAdvisedBean {
|
||||
public Object doStuff() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -38,6 +38,7 @@ import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
@EnableJpaRepositories("org.springframework.security.config.annotation.issue50.repo")
|
||||
@EnableTransactionManagement
|
||||
public class ApplicationConfig {
|
||||
|
||||
@Bean
|
||||
public DataSource dataSource() {
|
||||
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
|
||||
@@ -65,4 +66,5 @@ public class ApplicationConfig {
|
||||
txManager.setEntityManagerFactory(entityManagerFactory().getObject());
|
||||
return txManager;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -43,8 +43,9 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
*/
|
||||
@Transactional
|
||||
@RunWith(SpringRunner.class)
|
||||
@ContextConfiguration(classes = {ApplicationConfig.class, SecurityConfig.class})
|
||||
@ContextConfiguration(classes = { ApplicationConfig.class, SecurityConfig.class })
|
||||
public class Issue50Tests {
|
||||
|
||||
@Autowired
|
||||
private AuthenticationManager authenticationManager;
|
||||
|
||||
@@ -53,7 +54,8 @@ public class Issue50Tests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
SecurityContextHolder.getContext().setAuthentication(new TestingAuthenticationToken("test", null, "ROLE_ADMIN"));
|
||||
SecurityContextHolder.getContext()
|
||||
.setAuthentication(new TestingAuthenticationToken("test", null, "ROLE_ADMIN"));
|
||||
}
|
||||
|
||||
@After
|
||||
@@ -82,7 +84,7 @@ public class Issue50Tests {
|
||||
public void authenticateWhenValidUserThenAuthenticates() {
|
||||
this.userRepo.save(User.withUsernameAndPassword("test", "password"));
|
||||
Authentication result = this.authenticationManager
|
||||
.authenticate(new UsernamePasswordAuthenticationToken("test", "password"));
|
||||
.authenticate(new UsernamePasswordAuthenticationToken("test", "password"));
|
||||
assertThat(result.getName()).isEqualTo("test");
|
||||
}
|
||||
|
||||
@@ -91,6 +93,7 @@ public class Issue50Tests {
|
||||
SecurityContextHolder.getContext().setAuthentication(new TestingAuthenticationToken("test", null, "ROLE_USER"));
|
||||
this.userRepo.save(User.withUsernameAndPassword("denied", "password"));
|
||||
Authentication result = this.authenticationManager
|
||||
.authenticate(new UsernamePasswordAuthenticationToken("test", "password"));
|
||||
.authenticate(new UsernamePasswordAuthenticationToken("test", "password"));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -42,6 +42,7 @@ import org.springframework.util.Assert;
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@Configuration
|
||||
public class SecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
private UserRepository myUserRepository;
|
||||
|
||||
@@ -76,14 +77,12 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
return true;
|
||||
}
|
||||
|
||||
public Authentication authenticate(Authentication authentication)
|
||||
throws AuthenticationException {
|
||||
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
|
||||
Object principal = authentication.getPrincipal();
|
||||
String username = String.valueOf(principal);
|
||||
User user = myUserRepository.findByUsername(username);
|
||||
if (user == null) {
|
||||
throw new UsernameNotFoundException("No user for principal "
|
||||
+ principal);
|
||||
throw new UsernameNotFoundException("No user for principal " + principal);
|
||||
}
|
||||
if (!authentication.getCredentials().equals(user.getPassword())) {
|
||||
throw new BadCredentialsException("Invalid password");
|
||||
@@ -92,4 +91,5 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -63,6 +63,7 @@ public class User {
|
||||
User user = new User();
|
||||
user.setUsername(username);
|
||||
user.setPassword(password);
|
||||
return user;
|
||||
return user;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -27,4 +27,5 @@ public interface UserRepository extends CrudRepository<User, String> {
|
||||
|
||||
@PreAuthorize("hasRole('ROLE_ADMIN')")
|
||||
User findByUsername(String username);
|
||||
|
||||
}
|
||||
@@ -35,7 +35,7 @@ public class Authz {
|
||||
}
|
||||
|
||||
public boolean check(Authentication authentication, String message) {
|
||||
return message != null &&
|
||||
message.contains(authentication.getName());
|
||||
return message != null && message.contains(authentication.getName());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -22,6 +22,7 @@ import reactor.core.publisher.Flux;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
public class DelegatingReactiveMessageService implements ReactiveMessageService {
|
||||
|
||||
private final ReactiveMessageService delegate;
|
||||
|
||||
public DelegatingReactiveMessageService(ReactiveMessageService delegate) {
|
||||
@@ -41,29 +42,25 @@ public class DelegatingReactiveMessageService implements ReactiveMessageService
|
||||
|
||||
@Override
|
||||
@PreAuthorize("hasRole('ADMIN')")
|
||||
public Mono<String> monoPreAuthorizeHasRoleFindById(
|
||||
long id) {
|
||||
public Mono<String> monoPreAuthorizeHasRoleFindById(long id) {
|
||||
return delegate.monoPreAuthorizeHasRoleFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("returnObject?.contains(authentication?.name)")
|
||||
public Mono<String> monoPostAuthorizeFindById(
|
||||
long id) {
|
||||
public Mono<String> monoPostAuthorizeFindById(long id) {
|
||||
return delegate.monoPostAuthorizeFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PreAuthorize("@authz.check(#id)")
|
||||
public Mono<String> monoPreAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Mono<String> monoPreAuthorizeBeanFindById(long id) {
|
||||
return delegate.monoPreAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("@authz.check(authentication, returnObject)")
|
||||
public Mono<String> monoPostAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Mono<String> monoPostAuthorizeBeanFindById(long id) {
|
||||
return delegate.monoPostAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
@@ -74,29 +71,25 @@ public class DelegatingReactiveMessageService implements ReactiveMessageService
|
||||
|
||||
@Override
|
||||
@PreAuthorize("hasRole('ADMIN')")
|
||||
public Flux<String> fluxPreAuthorizeHasRoleFindById(
|
||||
long id) {
|
||||
public Flux<String> fluxPreAuthorizeHasRoleFindById(long id) {
|
||||
return delegate.fluxPreAuthorizeHasRoleFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("returnObject?.contains(authentication?.name)")
|
||||
public Flux<String> fluxPostAuthorizeFindById(
|
||||
long id) {
|
||||
public Flux<String> fluxPostAuthorizeFindById(long id) {
|
||||
return delegate.fluxPostAuthorizeFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PreAuthorize("@authz.check(#id)")
|
||||
public Flux<String> fluxPreAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Flux<String> fluxPreAuthorizeBeanFindById(long id) {
|
||||
return delegate.fluxPreAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("@authz.check(authentication, returnObject)")
|
||||
public Flux<String> fluxPostAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Flux<String> fluxPostAuthorizeBeanFindById(long id) {
|
||||
return delegate.fluxPostAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
@@ -107,29 +100,26 @@ public class DelegatingReactiveMessageService implements ReactiveMessageService
|
||||
|
||||
@Override
|
||||
@PreAuthorize("hasRole('ADMIN')")
|
||||
public Publisher<String> publisherPreAuthorizeHasRoleFindById(
|
||||
long id) {
|
||||
public Publisher<String> publisherPreAuthorizeHasRoleFindById(long id) {
|
||||
return delegate.publisherPreAuthorizeHasRoleFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("returnObject?.contains(authentication?.name)")
|
||||
public Publisher<String> publisherPostAuthorizeFindById(
|
||||
long id) {
|
||||
public Publisher<String> publisherPostAuthorizeFindById(long id) {
|
||||
return delegate.publisherPostAuthorizeFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PreAuthorize("@authz.check(#id)")
|
||||
public Publisher<String> publisherPreAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Publisher<String> publisherPreAuthorizeBeanFindById(long id) {
|
||||
return delegate.publisherPreAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
@Override
|
||||
@PostAuthorize("@authz.check(authentication, returnObject)")
|
||||
public Publisher<String> publisherPostAuthorizeBeanFindById(
|
||||
long id) {
|
||||
public Publisher<String> publisherPostAuthorizeBeanFindById(long id) {
|
||||
return delegate.publisherPostAuthorizeBeanFindById(id);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -44,12 +44,19 @@ import static org.mockito.Mockito.*;
|
||||
@RunWith(SpringRunner.class)
|
||||
@ContextConfiguration
|
||||
public class EnableReactiveMethodSecurityTests {
|
||||
@Autowired ReactiveMessageService messageService;
|
||||
|
||||
@Autowired
|
||||
ReactiveMessageService messageService;
|
||||
|
||||
ReactiveMessageService delegate;
|
||||
|
||||
TestPublisher<String> result = TestPublisher.create();
|
||||
|
||||
Context withAdmin = ReactiveSecurityContextHolder.withAuthentication(new TestingAuthenticationToken("admin", "password", "ROLE_USER", "ROLE_ADMIN"));
|
||||
Context withUser = ReactiveSecurityContextHolder.withAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
Context withAdmin = ReactiveSecurityContextHolder
|
||||
.withAuthentication(new TestingAuthenticationToken("admin", "password", "ROLE_USER", "ROLE_ADMIN"));
|
||||
|
||||
Context withUser = ReactiveSecurityContextHolder
|
||||
.withAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
|
||||
@After
|
||||
public void cleanup() {
|
||||
@@ -64,9 +71,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
@Test
|
||||
public void notPublisherPreAuthorizeFindByIdThenThrowsIllegalStateException() {
|
||||
assertThatThrownBy(() -> this.messageService.notPublisherPreAuthorizeFindById(1L))
|
||||
.isInstanceOf(IllegalStateException.class)
|
||||
.extracting(Throwable::getMessage)
|
||||
.isEqualTo("The returnType class java.lang.String on public abstract java.lang.String org.springframework.security.config.annotation.method.configuration.ReactiveMessageService.notPublisherPreAuthorizeFindById(long) must return an instance of org.reactivestreams.Publisher (i.e. Mono / Flux) in order to support Reactor Context");
|
||||
.isInstanceOf(IllegalStateException.class).extracting(Throwable::getMessage).isEqualTo(
|
||||
"The returnType class java.lang.String on public abstract java.lang.String org.springframework.security.config.annotation.method.configuration.ReactiveMessageService.notPublisherPreAuthorizeFindById(long) must return an instance of org.reactivestreams.Publisher (i.e. Mono / Flux) in order to support Reactor Context");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -82,21 +88,15 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void monoWhenPermitAllThenSuccess() {
|
||||
when(this.delegate.monoFindById(1L)).thenReturn(Mono.just("success"));
|
||||
|
||||
StepVerifier.create(this.delegate.monoFindById(1L))
|
||||
.expectNext("success")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(this.delegate.monoFindById(1L)).expectNext("success").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void monoPreAuthorizeHasRoleWhenGrantedThenSuccess() {
|
||||
when(this.delegate.monoPreAuthorizeHasRoleFindById(1L)).thenReturn(Mono.just("result"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeHasRoleFindById(1L)
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeHasRoleFindById(1L).subscriberContext(withAdmin);
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -104,10 +104,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.monoPreAuthorizeHasRoleFindById(1L)).thenReturn(Mono.from(result));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeHasRoleFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -116,12 +113,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void monoPreAuthorizeHasRoleWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.monoPreAuthorizeHasRoleFindById(1L)).thenReturn(Mono.from(result));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeHasRoleFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeHasRoleFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -130,12 +123,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void monoPreAuthorizeBeanWhenGrantedThenSuccess() {
|
||||
when(this.delegate.monoPreAuthorizeBeanFindById(2L)).thenReturn(Mono.just("result"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(2L)
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(2L).subscriberContext(withAdmin);
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -143,10 +132,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.monoPreAuthorizeBeanFindById(2L)).thenReturn(Mono.just("result"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -154,10 +140,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.monoPreAuthorizeBeanFindById(1L)).thenReturn(Mono.from(result));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -166,12 +149,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void monoPreAuthorizeBeanWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.monoPreAuthorizeBeanFindById(1L)).thenReturn(Mono.from(result));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Mono<String> findById = this.messageService.monoPreAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -180,36 +159,24 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void monoPostAuthorizeWhenAuthorizedThenSuccess() {
|
||||
when(this.delegate.monoPostAuthorizeFindById(1L)).thenReturn(Mono.just("user"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void monoPostAuthorizeWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.monoPostAuthorizeBeanFindById(1L)).thenReturn(Mono.just("not-authorized"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void monoPostAuthorizeWhenBeanAndAuthorizedThenSuccess() {
|
||||
when(this.delegate.monoPostAuthorizeBeanFindById(2L)).thenReturn(Mono.just("user"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(2L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(2L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -217,22 +184,15 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.monoPostAuthorizeBeanFindById(2L)).thenReturn(Mono.just("anonymous"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("anonymous")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("anonymous").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void monoPostAuthorizeWhenBeanAndNotAuthorizedThenDenied() {
|
||||
when(this.delegate.monoPostAuthorizeBeanFindById(1L)).thenReturn(Mono.just("not-authorized"));
|
||||
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Mono<String> findById = this.messageService.monoPostAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
// Flux tests
|
||||
@@ -250,20 +210,15 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void fluxWhenPermitAllThenSuccess() {
|
||||
when(this.delegate.fluxFindById(1L)).thenReturn(Flux.just("success"));
|
||||
|
||||
StepVerifier.create(this.delegate.fluxFindById(1L))
|
||||
.expectNext("success")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(this.delegate.fluxFindById(1L)).expectNext("success").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void fluxPreAuthorizeHasRoleWhenGrantedThenSuccess() {
|
||||
when(this.delegate.fluxPreAuthorizeHasRoleFindById(1L)).thenReturn(Flux.just("result"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeHasRoleFindById(1L)
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.consumeNextWith( s -> AssertionsForClassTypes.assertThat(s).isEqualTo("result"))
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeHasRoleFindById(1L).subscriberContext(withAdmin);
|
||||
StepVerifier.create(findById).consumeNextWith(s -> AssertionsForClassTypes.assertThat(s).isEqualTo("result"))
|
||||
.verifyComplete();
|
||||
}
|
||||
|
||||
@@ -272,10 +227,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.fluxPreAuthorizeHasRoleFindById(1L)).thenReturn(Flux.from(result));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeHasRoleFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -284,12 +236,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void fluxPreAuthorizeHasRoleWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.fluxPreAuthorizeHasRoleFindById(1L)).thenReturn(Flux.from(result));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeHasRoleFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeHasRoleFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -298,12 +246,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void fluxPreAuthorizeBeanWhenGrantedThenSuccess() {
|
||||
when(this.delegate.fluxPreAuthorizeBeanFindById(2L)).thenReturn(Flux.just("result"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(2L)
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(2L).subscriberContext(withAdmin);
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -311,10 +255,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.fluxPreAuthorizeBeanFindById(2L)).thenReturn(Flux.just("result"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -322,10 +263,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.fluxPreAuthorizeBeanFindById(1L)).thenReturn(Flux.from(result));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -334,12 +272,8 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void fluxPreAuthorizeBeanWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.fluxPreAuthorizeBeanFindById(1L)).thenReturn(Flux.from(result));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Flux<String> findById = this.messageService.fluxPreAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -348,36 +282,24 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void fluxPostAuthorizeWhenAuthorizedThenSuccess() {
|
||||
when(this.delegate.fluxPostAuthorizeFindById(1L)).thenReturn(Flux.just("user"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void fluxPostAuthorizeWhenNotAuthorizedThenDenied() {
|
||||
when(this.delegate.fluxPostAuthorizeBeanFindById(1L)).thenReturn(Flux.just("not-authorized"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void fluxPostAuthorizeWhenBeanAndAuthorizedThenSuccess() {
|
||||
when(this.delegate.fluxPostAuthorizeBeanFindById(2L)).thenReturn(Flux.just("user"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(2L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(2L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -385,22 +307,15 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.fluxPostAuthorizeBeanFindById(2L)).thenReturn(Flux.just("anonymous"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("anonymous")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("anonymous").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void fluxPostAuthorizeWhenBeanAndNotAuthorizedThenDenied() {
|
||||
when(this.delegate.fluxPostAuthorizeBeanFindById(1L)).thenReturn(Flux.just("not-authorized"));
|
||||
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(1L)
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
Flux<String> findById = this.messageService.fluxPostAuthorizeBeanFindById(1L).subscriberContext(withUser);
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
// Publisher tests
|
||||
@@ -418,9 +333,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public void publisherWhenPermitAllThenSuccess() {
|
||||
when(this.delegate.publisherFindById(1L)).thenReturn(publisherJust("success"));
|
||||
|
||||
StepVerifier.create(this.delegate.publisherFindById(1L))
|
||||
.expectNext("success")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(this.delegate.publisherFindById(1L)).expectNext("success").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -429,9 +342,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPreAuthorizeHasRoleFindById(1L))
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.consumeNextWith( s -> AssertionsForClassTypes.assertThat(s).isEqualTo("result"))
|
||||
StepVerifier.create(findById).consumeNextWith(s -> AssertionsForClassTypes.assertThat(s).isEqualTo("result"))
|
||||
.verifyComplete();
|
||||
}
|
||||
|
||||
@@ -440,10 +351,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.publisherPreAuthorizeHasRoleFindById(1L)).thenReturn(result);
|
||||
|
||||
Publisher<String> findById = this.messageService.publisherPreAuthorizeHasRoleFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -454,10 +362,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPreAuthorizeHasRoleFindById(1L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -468,10 +373,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPreAuthorizeBeanFindById(2L))
|
||||
.subscriberContext(withAdmin);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -479,10 +381,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.publisherPreAuthorizeBeanFindById(2L)).thenReturn(publisherJust("result"));
|
||||
|
||||
Publisher<String> findById = this.messageService.publisherPreAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("result")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("result").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -490,10 +389,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.publisherPreAuthorizeBeanFindById(1L)).thenReturn(result);
|
||||
|
||||
Publisher<String> findById = this.messageService.publisherPreAuthorizeBeanFindById(1L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -504,10 +400,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPreAuthorizeBeanFindById(1L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
|
||||
result.assertNoSubscribers();
|
||||
}
|
||||
@@ -518,10 +411,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPostAuthorizeFindById(1L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -530,10 +420,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPostAuthorizeBeanFindById(1L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -542,10 +429,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPostAuthorizeBeanFindById(2L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -553,10 +437,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
when(this.delegate.publisherPostAuthorizeBeanFindById(2L)).thenReturn(publisherJust("anonymous"));
|
||||
|
||||
Publisher<String> findById = this.messageService.publisherPostAuthorizeBeanFindById(2L);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectNext("anonymous")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(findById).expectNext("anonymous").verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -565,10 +446,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
Publisher<String> findById = Flux.from(this.messageService.publisherPostAuthorizeBeanFindById(1L))
|
||||
.subscriberContext(withUser);
|
||||
StepVerifier
|
||||
.create(findById)
|
||||
.expectError(AccessDeniedException.class)
|
||||
.verify();
|
||||
StepVerifier.create(findById).expectError(AccessDeniedException.class).verify();
|
||||
}
|
||||
|
||||
static <T> Publisher<T> publisher(Flux<T> flux) {
|
||||
@@ -581,6 +459,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
|
||||
@EnableReactiveMethodSecurity
|
||||
static class Config {
|
||||
|
||||
ReactiveMessageService delegate = mock(ReactiveMessageService.class);
|
||||
|
||||
@Bean
|
||||
@@ -592,5 +471,7 @@ public class EnableReactiveMethodSecurityTests {
|
||||
public Authz authz() {
|
||||
return new Authz();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -68,13 +68,13 @@ import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @author Artsiom Yudovin
|
||||
*/
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@SecurityTestExecutionListeners
|
||||
public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -112,11 +112,13 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@EnableGlobalMethodSecurity
|
||||
public static class CustomMetadataSourceConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
@Bean
|
||||
@Override
|
||||
protected MethodSecurityMetadataSource customMethodSecurityMetadataSource() {
|
||||
return mock(MethodSecurityMetadataSource.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -125,13 +127,17 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
try {
|
||||
this.authenticationManager.authenticate(new UsernamePasswordAuthenticationToken("foo", "bar"));
|
||||
} catch(AuthenticationException e) {}
|
||||
}
|
||||
catch (AuthenticationException e) {
|
||||
}
|
||||
|
||||
assertThat(this.events.getEvents()).extracting(Object::getClass).containsOnly((Class) AuthenticationFailureBadCredentialsEvent.class);
|
||||
assertThat(this.events.getEvents()).extracting(Object::getClass)
|
||||
.containsOnly((Class) AuthenticationFailureBadCredentialsEvent.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class InMemoryAuthWithGlobalMethodSecurityConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -142,8 +148,10 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@Bean
|
||||
public MockEventListener<AbstractAuthenticationEvent> listener() {
|
||||
return new MockEventListener<AbstractAuthenticationEvent>() {};
|
||||
return new MockEventListener<AbstractAuthenticationEvent>() {
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -154,8 +162,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
AuthenticationTrustResolver trustResolver = this.spring.getContext().getBean(AuthenticationTrustResolver.class);
|
||||
when(trustResolver.isAnonymous(any())).thenReturn(true, false);
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeNotAnonymous())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeNotAnonymous()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
this.service.preAuthorizeNotAnonymous();
|
||||
|
||||
@@ -174,6 +181,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public MethodSecurityServiceImpl service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2301
|
||||
@@ -183,8 +191,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
this.spring.register(ExpressionHandlerHasBeanResolverSetConfig.class).autowire();
|
||||
Authz authz = this.spring.getContext().getBean(Authz.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeBean(false))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeBean(false)).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
this.service.preAuthorizeBean(true);
|
||||
}
|
||||
@@ -201,6 +208,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public Authz authz() {
|
||||
return new Authz();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -208,8 +216,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void methodSecuritySupportsAnnotaitonsOnInterfaceParamerNames() {
|
||||
this.spring.register(MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.postAnnotation("deny"))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.postAnnotation("deny")).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
this.service.postAnnotation("grant");
|
||||
// no exception
|
||||
@@ -222,6 +229,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -234,8 +242,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
this.service.hasPermission("something");
|
||||
// no exception
|
||||
|
||||
assertThatThrownBy(() -> this.service.hasPermission("something"))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.hasPermission("something")).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@@ -250,6 +257,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -271,6 +279,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public PermissionEvaluator permissionEvaluator2() {
|
||||
return mock(PermissionEvaluator.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2425
|
||||
@@ -279,12 +288,13 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void enableGlobalMethodSecurityWorksOnSuperclass() {
|
||||
this.spring.register(ChildConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class ChildConfig extends ParentConfig {}
|
||||
static class ChildConfig extends ParentConfig {
|
||||
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
static class ParentConfig {
|
||||
@@ -293,6 +303,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2479
|
||||
@@ -308,26 +319,29 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
child.refresh();
|
||||
this.spring.context(child).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class Sec2479ParentConfig {
|
||||
|
||||
@Bean
|
||||
public AuthenticationManager am() {
|
||||
return mock(AuthenticationManager.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
static class Sec2479ChildConfig {
|
||||
|
||||
@Bean
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -342,6 +356,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
static class Sec2815Config {
|
||||
|
||||
@Bean
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -359,6 +374,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
static class AuthConfig extends GlobalAuthenticationConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
DataSource dataSource;
|
||||
|
||||
@@ -366,16 +382,19 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class MockBeanPostProcessor implements BeanPostProcessor {
|
||||
|
||||
Map<String, Object> beforeInit = new HashMap<>();
|
||||
|
||||
Map<String, Object> afterInit = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName) throws
|
||||
BeansException {
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
|
||||
this.beforeInit.put(beanName, bean);
|
||||
return bean;
|
||||
}
|
||||
@@ -385,6 +404,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
this.afterInit.put(beanName, bean);
|
||||
return bean;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-3045
|
||||
@@ -392,12 +412,13 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void globalSecurityProxiesSecurity() {
|
||||
this.spring.register(Sec3005Config.class).autowire();
|
||||
|
||||
assertThat(this.service.getClass()).matches(c-> !Proxy.isProxyClass(c), "is not proxy class");
|
||||
assertThat(this.service.getClass()).matches(c -> !Proxy.isProxyClass(c), "is not proxy class");
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true, mode= AdviceMode.ASPECTJ)
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true, mode = AdviceMode.ASPECTJ)
|
||||
@EnableTransactionManagement
|
||||
static class Sec3005Config {
|
||||
|
||||
@Bean
|
||||
public MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -407,25 +428,26 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
// // gh-3797
|
||||
// def preAuthorizeBeanSpel() {
|
||||
// setup:
|
||||
// SecurityContextHolder.getContext().setAuthentication(
|
||||
// new TestingAuthenticationToken("user", "password","ROLE_USER"))
|
||||
// context = new AnnotationConfigApplicationContext(PreAuthorizeBeanSpelConfig)
|
||||
// BeanSpelService service = context.getBean(BeanSpelService)
|
||||
// when:
|
||||
// service.run(true)
|
||||
// then:
|
||||
// noExceptionThrown()
|
||||
// when:
|
||||
// service.run(false)
|
||||
// then:
|
||||
// thrown(AccessDeniedException)
|
||||
// }
|
||||
// // gh-3797
|
||||
// def preAuthorizeBeanSpel() {
|
||||
// setup:
|
||||
// SecurityContextHolder.getContext().setAuthentication(
|
||||
// new TestingAuthenticationToken("user", "password","ROLE_USER"))
|
||||
// context = new AnnotationConfigApplicationContext(PreAuthorizeBeanSpelConfig)
|
||||
// BeanSpelService service = context.getBean(BeanSpelService)
|
||||
// when:
|
||||
// service.run(true)
|
||||
// then:
|
||||
// noExceptionThrown()
|
||||
// when:
|
||||
// service.run(false)
|
||||
// then:
|
||||
// thrown(AccessDeniedException)
|
||||
// }
|
||||
//
|
||||
|
||||
@Test
|
||||
@@ -433,8 +455,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void preAuthorizeBeanSpel() {
|
||||
this.spring.register(PreAuthorizeBeanSpelConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeBean(false))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorizeBean(false)).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
this.service.preAuthorizeBean(true);
|
||||
}
|
||||
@@ -442,6 +463,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
@Configuration
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class PreAuthorizeBeanSpelConfig {
|
||||
|
||||
@Bean
|
||||
MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -451,6 +473,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
Authz authz() {
|
||||
return new Authz();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-3394
|
||||
@@ -459,14 +482,14 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void roleHierarchy() {
|
||||
this.spring.register(RoleHierarchyConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
this.service.preAuthorizeAdmin();
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@Configuration
|
||||
public static class RoleHierarchyConfig {
|
||||
|
||||
@Bean
|
||||
MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -478,6 +501,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
result.setHierarchy("ROLE_USER > ROLE_ADMIN");
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -485,11 +509,10 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
public void grantedAuthorityDefaultsAutowires() {
|
||||
this.spring.register(CustomGrantedAuthorityConfig.class).autowire();
|
||||
|
||||
CustomGrantedAuthorityConfig.CustomAuthorityService customService = this.spring.getContext().getBean(
|
||||
CustomGrantedAuthorityConfig.CustomAuthorityService.class);
|
||||
CustomGrantedAuthorityConfig.CustomAuthorityService customService = this.spring.getContext()
|
||||
.getBean(CustomGrantedAuthorityConfig.CustomAuthorityService.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
customService.customPrefixRoleUser();
|
||||
// no exception
|
||||
@@ -514,9 +537,13 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
}
|
||||
|
||||
static class CustomAuthorityService {
|
||||
|
||||
@PreAuthorize("hasRole('ROLE:USER')")
|
||||
public void customPrefixRoleUser() {}
|
||||
public void customPrefixRoleUser() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -527,8 +554,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
EmptyRolePrefixGrantedAuthorityConfig.CustomAuthorityService customService = this.spring.getContext()
|
||||
.getBean(EmptyRolePrefixGrantedAuthorityConfig.CustomAuthorityService.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.securedUser())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.securedUser()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
customService.emptyPrefixRoleUser();
|
||||
// no exception
|
||||
@@ -536,6 +562,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
|
||||
@EnableGlobalMethodSecurity(securedEnabled = true)
|
||||
static class EmptyRolePrefixGrantedAuthorityConfig {
|
||||
|
||||
@Bean
|
||||
public GrantedAuthorityDefaults ga() {
|
||||
return new GrantedAuthorityDefaults("");
|
||||
@@ -552,18 +579,22 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
}
|
||||
|
||||
static class CustomAuthorityService {
|
||||
|
||||
@Secured("USER")
|
||||
public void emptyPrefixRoleUser() {}
|
||||
public void emptyPrefixRoleUser() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void methodSecurityInterceptorUsesMetadataSourceBeanWhenProxyingDisabled() {
|
||||
this.spring.register(CustomMetadataSourceBeanProxyEnabledConfig.class).autowire();
|
||||
MethodSecurityInterceptor methodInterceptor =
|
||||
(MethodSecurityInterceptor) this.spring.getContext().getBean(MethodInterceptor.class);
|
||||
MethodSecurityMetadataSource methodSecurityMetadataSource =
|
||||
this.spring.getContext().getBean(MethodSecurityMetadataSource.class);
|
||||
MethodSecurityInterceptor methodInterceptor = (MethodSecurityInterceptor) this.spring.getContext()
|
||||
.getBean(MethodInterceptor.class);
|
||||
MethodSecurityMetadataSource methodSecurityMetadataSource = this.spring.getContext()
|
||||
.getBean(MethodSecurityMetadataSource.class);
|
||||
|
||||
assertThat(methodInterceptor.getSecurityMetadataSource()).isSameAs(methodSecurityMetadataSource);
|
||||
}
|
||||
@@ -571,5 +602,7 @@ public class GlobalMethodSecurityConfigurationTests {
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@Configuration
|
||||
public static class CustomMetadataSourceBeanProxyEnabledConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ import javax.annotation.security.PermitAll;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public interface MethodSecurityService {
|
||||
|
||||
@PreAuthorize("denyAll")
|
||||
String preAuthorize();
|
||||
|
||||
@@ -67,4 +68,5 @@ public interface MethodSecurityService {
|
||||
|
||||
@PostAuthorize("#o?.contains('grant')")
|
||||
String postAnnotation(@P("o") String object);
|
||||
|
||||
}
|
||||
|
||||
@@ -21,8 +21,10 @@ import org.springframework.context.annotation.Bean;
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
public class MethodSecurityServiceConfig {
|
||||
|
||||
@Bean
|
||||
MethodSecurityService service() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -23,6 +23,7 @@ import org.springframework.security.core.context.SecurityContextHolder;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class MethodSecurityServiceImpl implements MethodSecurityService {
|
||||
|
||||
@Override
|
||||
public String preAuthorize() {
|
||||
return null;
|
||||
|
||||
@@ -35,7 +35,6 @@ import static org.assertj.core.api.Assertions.assertThatCode;
|
||||
import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
@@ -54,11 +53,9 @@ public class NamespaceGlobalMethodSecurityExpressionHandlerTests {
|
||||
public void methodSecurityWhenUsingCustomPermissionEvaluatorThenPreAuthorizesAccordingly() {
|
||||
this.spring.register(CustomAccessDecisionManagerConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.hasPermission("granted"))
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.hasPermission("granted")).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.hasPermission("denied"))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.hasPermission("denied")).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -66,30 +63,33 @@ public class NamespaceGlobalMethodSecurityExpressionHandlerTests {
|
||||
public void methodSecurityWhenUsingCustomPermissionEvaluatorThenPostAuthorizesAccordingly() {
|
||||
this.spring.register(CustomAccessDecisionManagerConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.postHasPermission("granted"))
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.postHasPermission("granted")).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.postHasPermission("denied"))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.postHasPermission("denied")).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class CustomAccessDecisionManagerConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
@Override
|
||||
protected MethodSecurityExpressionHandler createExpressionHandler() {
|
||||
DefaultMethodSecurityExpressionHandler expressionHandler = new DefaultMethodSecurityExpressionHandler();
|
||||
|
||||
expressionHandler.setPermissionEvaluator(new PermissionEvaluator() {
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject,
|
||||
Object permission) {
|
||||
return "granted".equals(targetDomainObject);
|
||||
}
|
||||
|
||||
public boolean hasPermission(Authentication authentication, Serializable targetId, String targetType, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Serializable targetId, String targetType,
|
||||
Object permission) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
});
|
||||
|
||||
return expressionHandler;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -60,7 +60,6 @@ import static org.assertj.core.api.Assertions.assertThatCode;
|
||||
import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
@@ -81,11 +80,9 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenCustomAccessDecisionManagerThenAuthorizes() {
|
||||
this.spring.register(CustomAccessDecisionManagerConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.secured())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.secured()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
}
|
||||
|
||||
@@ -98,16 +95,22 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
}
|
||||
|
||||
public static class DenyAllAccessDecisionManager implements AccessDecisionManager {
|
||||
public void decide(Authentication authentication, Object object, Collection<ConfigAttribute> configAttributes) {
|
||||
|
||||
public void decide(Authentication authentication, Object object,
|
||||
Collection<ConfigAttribute> configAttributes) {
|
||||
throw new AccessDeniedException("Always Denied");
|
||||
}
|
||||
|
||||
public boolean supports(ConfigAttribute attribute) {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean supports(Class<?> clazz) {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- after-invocation-provider
|
||||
@@ -117,13 +120,11 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenCustomAfterInvocationManagerThenAuthorizes() {
|
||||
this.spring.register(CustomAfterInvocationManagerConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorizePermitAll())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorizePermitAll()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class CustomAfterInvocationManagerConfig
|
||||
extends GlobalMethodSecurityConfiguration {
|
||||
public static class CustomAfterInvocationManagerConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
@Override
|
||||
protected AfterInvocationManager afterInvocationManager() {
|
||||
@@ -131,10 +132,9 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
}
|
||||
|
||||
public static class AfterInvocationManagerStub implements AfterInvocationManager {
|
||||
public Object decide(Authentication authentication,
|
||||
Object object,
|
||||
Collection<ConfigAttribute> attributes,
|
||||
Object returnedObject) throws AccessDeniedException {
|
||||
|
||||
public Object decide(Authentication authentication, Object object, Collection<ConfigAttribute> attributes,
|
||||
Object returnedObject) throws AccessDeniedException {
|
||||
|
||||
throw new AccessDeniedException("custom AfterInvocationManager");
|
||||
}
|
||||
@@ -142,10 +142,13 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public boolean supports(ConfigAttribute attribute) {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean supports(Class<?> clazz) {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- authentication-manager-ref ---
|
||||
@@ -155,8 +158,7 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenCustomAuthenticationManagerThenAuthorizes() {
|
||||
this.spring.register(CustomAuthenticationConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(UnsupportedOperationException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(UnsupportedOperationException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@@ -175,6 +177,7 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
throw new UnsupportedOperationException();
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- jsr250-annotations ---
|
||||
@@ -184,17 +187,13 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenJsr250EnabledThenAuthorizes() {
|
||||
this.spring.register(Jsr250Config.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.preAuthorize())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.preAuthorize()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.secured())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.secured()).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.jsr250())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.jsr250()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
assertThatCode(() -> this.service.jsr250PermitAll())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.jsr250PermitAll()).doesNotThrowAnyException();
|
||||
|
||||
}
|
||||
|
||||
@@ -209,16 +208,14 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void methodSecurityWhenCustomMethodSecurityMetadataSourceThenAuthorizes() {
|
||||
this.spring.register(CustomMethodSecurityMetadataSourceConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
this.spring.register(CustomMethodSecurityMetadataSourceConfig.class, MethodSecurityServiceConfig.class)
|
||||
.autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.secured())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.secured()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.jsr250())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.jsr250()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity
|
||||
@@ -228,16 +225,18 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
protected MethodSecurityMetadataSource customMethodSecurityMetadataSource() {
|
||||
return new AbstractMethodSecurityMetadataSource() {
|
||||
public Collection<ConfigAttribute> getAttributes(Method method, Class<?> targetClass) {
|
||||
// require ROLE_NOBODY for any method on MethodSecurityService interface
|
||||
return MethodSecurityService.class.isAssignableFrom(targetClass) ?
|
||||
Arrays.asList(new SecurityConfig("ROLE_NOBODY")) :
|
||||
Collections.emptyList();
|
||||
// require ROLE_NOBODY for any method on MethodSecurityService
|
||||
// interface
|
||||
return MethodSecurityService.class.isAssignableFrom(targetClass)
|
||||
? Arrays.asList(new SecurityConfig("ROLE_NOBODY")) : Collections.emptyList();
|
||||
}
|
||||
|
||||
public Collection<ConfigAttribute> getAllConfigAttributes() {
|
||||
return null;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- mode ---
|
||||
@@ -247,10 +246,13 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void contextRefreshWhenUsingAspectJThenAutowire() throws Exception {
|
||||
this.spring.register(AspectJModeConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(Class.forName("org.springframework.security.access.intercept.aspectj.aspect.AnnotationSecurityAspect"))).isNotNull();
|
||||
assertThat(this.spring.getContext().getBean(
|
||||
Class.forName("org.springframework.security.access.intercept.aspectj.aspect.AnnotationSecurityAspect")))
|
||||
.isNotNull();
|
||||
assertThat(this.spring.getContext().getBean(AspectJMethodSecurityInterceptor.class)).isNotNull();
|
||||
|
||||
//TODO diagnose why aspectj isn't weaving method security advice around MethodSecurityServiceImpl
|
||||
// TODO diagnose why aspectj isn't weaving method security advice around
|
||||
// MethodSecurityServiceImpl
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(mode = AdviceMode.ASPECTJ, securedEnabled = true)
|
||||
@@ -260,48 +262,51 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
|
||||
@Test
|
||||
public void contextRefreshWhenUsingAspectJAndCustomGlobalMethodSecurityConfigurationThenAutowire()
|
||||
throws Exception {
|
||||
throws Exception {
|
||||
|
||||
this.spring.register(AspectJModeExtendsGMSCConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(Class.forName("org.springframework.security.access.intercept.aspectj.aspect.AnnotationSecurityAspect"))).isNotNull();
|
||||
assertThat(this.spring.getContext().getBean(
|
||||
Class.forName("org.springframework.security.access.intercept.aspectj.aspect.AnnotationSecurityAspect")))
|
||||
.isNotNull();
|
||||
assertThat(this.spring.getContext().getBean(AspectJMethodSecurityInterceptor.class)).isNotNull();
|
||||
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(mode = AdviceMode.ASPECTJ, securedEnabled = true)
|
||||
public static class AspectJModeExtendsGMSCConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
// --- order ---
|
||||
|
||||
private static class AdvisorOrderConfig
|
||||
implements ImportBeanDefinitionRegistrar {
|
||||
private static class AdvisorOrderConfig implements ImportBeanDefinitionRegistrar {
|
||||
|
||||
private static class ExceptingInterceptor implements MethodInterceptor {
|
||||
|
||||
@Override
|
||||
public Object invoke(MethodInvocation invocation) {
|
||||
throw new UnsupportedOperationException("Deny All");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
|
||||
BeanDefinitionBuilder advice = BeanDefinitionBuilder
|
||||
.rootBeanDefinition(ExceptingInterceptor.class);
|
||||
registry.registerBeanDefinition("exceptingInterceptor",
|
||||
advice.getBeanDefinition());
|
||||
public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata,
|
||||
BeanDefinitionRegistry registry) {
|
||||
BeanDefinitionBuilder advice = BeanDefinitionBuilder.rootBeanDefinition(ExceptingInterceptor.class);
|
||||
registry.registerBeanDefinition("exceptingInterceptor", advice.getBeanDefinition());
|
||||
|
||||
BeanDefinitionBuilder advisor = BeanDefinitionBuilder
|
||||
.rootBeanDefinition(MethodSecurityMetadataSourceAdvisor.class);
|
||||
.rootBeanDefinition(MethodSecurityMetadataSourceAdvisor.class);
|
||||
advisor.setRole(BeanDefinition.ROLE_INFRASTRUCTURE);
|
||||
advisor.addConstructorArgValue("exceptingInterceptor");
|
||||
advisor.addConstructorArgReference("methodSecurityMetadataSource");
|
||||
advisor.addConstructorArgValue("methodSecurityMetadataSource");
|
||||
advisor.addPropertyValue("order", 0);
|
||||
registry.registerBeanDefinition("exceptingAdvisor",
|
||||
advisor.getBeanDefinition());
|
||||
registry.registerBeanDefinition("exceptingAdvisor", advisor.getBeanDefinition());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -309,13 +314,10 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenOrderSpecifiedThenConfigured() {
|
||||
this.spring.register(CustomOrderConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext()
|
||||
.getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder())
|
||||
.isEqualTo(-135);
|
||||
assertThat(this.spring.getContext().getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder()).isEqualTo(-135);
|
||||
|
||||
assertThatThrownBy(() -> this.service.jsr250())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.jsr250()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(order = -135, jsr250Enabled = true)
|
||||
@@ -329,37 +331,34 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenOrderUnspecifiedThenConfiguredToLowestPrecedence() {
|
||||
this.spring.register(DefaultOrderConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext()
|
||||
.getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder())
|
||||
.isEqualTo(Ordered.LOWEST_PRECEDENCE);
|
||||
assertThat(this.spring.getContext().getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder()).isEqualTo(Ordered.LOWEST_PRECEDENCE);
|
||||
|
||||
assertThatThrownBy(() -> this.service.jsr250())
|
||||
.isInstanceOf(UnsupportedOperationException.class);
|
||||
assertThatThrownBy(() -> this.service.jsr250()).isInstanceOf(UnsupportedOperationException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(jsr250Enabled = true)
|
||||
@Import(AdvisorOrderConfig.class)
|
||||
public static class DefaultOrderConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void methodSecurityWhenOrderUnspecifiedAndCustomGlobalMethodSecurityConfigurationThenConfiguredToLowestPrecedence() {
|
||||
this.spring.register(DefaultOrderExtendsMethodSecurityConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
this.spring.register(DefaultOrderExtendsMethodSecurityConfig.class, MethodSecurityServiceConfig.class)
|
||||
.autowire();
|
||||
|
||||
assertThat(this.spring.getContext()
|
||||
.getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder())
|
||||
.isEqualTo(Ordered.LOWEST_PRECEDENCE);
|
||||
assertThat(this.spring.getContext().getBean("metaDataSourceAdvisor", MethodSecurityMetadataSourceAdvisor.class)
|
||||
.getOrder()).isEqualTo(Ordered.LOWEST_PRECEDENCE);
|
||||
|
||||
assertThatThrownBy(() -> this.service.jsr250())
|
||||
.isInstanceOf(UnsupportedOperationException.class);
|
||||
assertThatThrownBy(() -> this.service.jsr250()).isInstanceOf(UnsupportedOperationException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(jsr250Enabled = true)
|
||||
@Import(AdvisorOrderConfig.class)
|
||||
public static class DefaultOrderExtendsMethodSecurityConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
// --- pre-post-annotations ---
|
||||
@@ -369,18 +368,16 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenPrePostEnabledThenPreAuthorizes() {
|
||||
this.spring.register(PreAuthorizeConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.secured())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.secured()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.jsr250())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.jsr250()).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class PreAuthorizeConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -388,18 +385,16 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenPrePostEnabledAndCustomGlobalMethodSecurityConfigurationThenPreAuthorizes() {
|
||||
this.spring.register(PreAuthorizeExtendsGMSCConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.secured())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.secured()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.jsr250())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.jsr250()).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class PreAuthorizeExtendsGMSCConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
// --- proxy-target-class ---
|
||||
@@ -410,15 +405,14 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
this.spring.register(ProxyTargetClassConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
// make sure service was actually proxied
|
||||
assertThat(this.service.getClass().getInterfaces())
|
||||
.doesNotContain(MethodSecurityService.class);
|
||||
assertThat(this.service.getClass().getInterfaces()).doesNotContain(MethodSecurityService.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(proxyTargetClass = true, prePostEnabled = true)
|
||||
public static class ProxyTargetClassConfig {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -426,15 +420,14 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenDefaultProxyThenWiresToInterface() {
|
||||
this.spring.register(DefaultProxyConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThat(this.service.getClass().getInterfaces())
|
||||
.contains(MethodSecurityService.class);
|
||||
assertThat(this.service.getClass().getInterfaces()).contains(MethodSecurityService.class);
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class DefaultProxyConfig {
|
||||
|
||||
}
|
||||
|
||||
// --- run-as-manager-ref ---
|
||||
@@ -445,7 +438,7 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
this.spring.register(CustomRunAsManagerConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThat(service.runAs().getAuthorities())
|
||||
.anyMatch(authority -> "ROLE_RUN_AS_SUPER".equals(authority.getAuthority()));
|
||||
.anyMatch(authority -> "ROLE_RUN_AS_SUPER".equals(authority.getAuthority()));
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(securedEnabled = true)
|
||||
@@ -457,6 +450,7 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
runAsManager.setKey("some key");
|
||||
return runAsManager;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- secured-annotation ---
|
||||
@@ -466,21 +460,18 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenSecuredEnabledThenSecures() {
|
||||
this.spring.register(SecuredConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatThrownBy(() -> this.service.secured())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.secured()).isInstanceOf(AccessDeniedException.class);
|
||||
|
||||
assertThatCode(() -> this.service.securedUser())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.securedUser()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.preAuthorize())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.preAuthorize()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.jsr250())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.jsr250()).doesNotThrowAnyException();
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(securedEnabled = true)
|
||||
public static class SecuredConfig {
|
||||
|
||||
}
|
||||
|
||||
// --- unsorted ---
|
||||
@@ -488,14 +479,13 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void methodSecurityWhenMissingEnableAnnotationThenShowsHelpfulError() {
|
||||
assertThatThrownBy(() ->
|
||||
this.spring.register(ExtendsNoEnableAnntotationConfig.class).autowire())
|
||||
.hasStackTraceContaining(EnableGlobalMethodSecurity.class.getName() + " is required");
|
||||
assertThatThrownBy(() -> this.spring.register(ExtendsNoEnableAnntotationConfig.class).autowire())
|
||||
.hasStackTraceContaining(EnableGlobalMethodSecurity.class.getName() + " is required");
|
||||
}
|
||||
|
||||
@Configuration
|
||||
public static class ExtendsNoEnableAnntotationConfig
|
||||
extends GlobalMethodSecurityConfiguration {
|
||||
public static class ExtendsNoEnableAnntotationConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -503,18 +493,17 @@ public class NamespaceGlobalMethodSecurityTests {
|
||||
public void methodSecurityWhenImportingGlobalMethodSecurityConfigurationSubclassThenAuthorizes() {
|
||||
this.spring.register(ImportSubclassGMSCConfig.class, MethodSecurityServiceConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> this.service.secured())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.secured()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> this.service.jsr250())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> this.service.jsr250()).doesNotThrowAnyException();
|
||||
|
||||
assertThatThrownBy(() -> this.service.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.service.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Import(PreAuthorizeExtendsGMSCConfig.class)
|
||||
public static class ImportSubclassGMSCConfig {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -20,23 +20,37 @@ import reactor.core.publisher.Flux;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
public interface ReactiveMessageService {
|
||||
|
||||
String notPublisherPreAuthorizeFindById(long id);
|
||||
|
||||
Mono<String> monoFindById(long id);
|
||||
|
||||
Mono<String> monoPreAuthorizeHasRoleFindById(long id);
|
||||
|
||||
Mono<String> monoPostAuthorizeFindById(long id);
|
||||
|
||||
Mono<String> monoPreAuthorizeBeanFindById(long id);
|
||||
|
||||
Mono<String> monoPostAuthorizeBeanFindById(long id);
|
||||
|
||||
Flux<String> fluxFindById(long id);
|
||||
|
||||
Flux<String> fluxPreAuthorizeHasRoleFindById(long id);
|
||||
|
||||
Flux<String> fluxPostAuthorizeFindById(long id);
|
||||
|
||||
Flux<String> fluxPreAuthorizeBeanFindById(long id);
|
||||
|
||||
Flux<String> fluxPostAuthorizeBeanFindById(long id);
|
||||
|
||||
Publisher<String> publisherFindById(long id);
|
||||
|
||||
Publisher<String> publisherPreAuthorizeHasRoleFindById(long id);
|
||||
|
||||
Publisher<String> publisherPostAuthorizeFindById(long id);
|
||||
|
||||
Publisher<String> publisherPreAuthorizeBeanFindById(long id);
|
||||
|
||||
Publisher<String> publisherPostAuthorizeBeanFindById(long id);
|
||||
|
||||
}
|
||||
|
||||
@@ -46,14 +46,13 @@ public class ReactiveMethodSecurityConfigurationTests {
|
||||
public void rolePrefixWithGrantedAuthorityDefaults() throws NoSuchMethodException {
|
||||
this.spring.register(WithRolePrefixConfiguration.class).autowire();
|
||||
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken(
|
||||
"principal", "credential", "CUSTOM_ABC");
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("principal", "credential",
|
||||
"CUSTOM_ABC");
|
||||
MockMethodInvocation methodInvocation = new MockMethodInvocation(new Foo(), Foo.class, "bar", String.class);
|
||||
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler
|
||||
.createEvaluationContext(authentication, methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject()
|
||||
.getValue();
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler.createEvaluationContext(authentication,
|
||||
methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject().getValue();
|
||||
|
||||
assertThat(root.hasRole("ROLE_ABC")).isFalse();
|
||||
assertThat(root.hasRole("ROLE_CUSTOM_ABC")).isFalse();
|
||||
@@ -65,14 +64,13 @@ public class ReactiveMethodSecurityConfigurationTests {
|
||||
public void rolePrefixWithDefaultConfig() throws NoSuchMethodException {
|
||||
this.spring.register(ReactiveMethodSecurityConfiguration.class).autowire();
|
||||
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken(
|
||||
"principal", "credential", "ROLE_ABC");
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("principal", "credential",
|
||||
"ROLE_ABC");
|
||||
MockMethodInvocation methodInvocation = new MockMethodInvocation(new Foo(), Foo.class, "bar", String.class);
|
||||
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler
|
||||
.createEvaluationContext(authentication, methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject()
|
||||
.getValue();
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler.createEvaluationContext(authentication,
|
||||
methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject().getValue();
|
||||
|
||||
assertThat(root.hasRole("ROLE_ABC")).isTrue();
|
||||
assertThat(root.hasRole("ABC")).isTrue();
|
||||
@@ -81,24 +79,25 @@ public class ReactiveMethodSecurityConfigurationTests {
|
||||
@Configuration
|
||||
@EnableReactiveMethodSecurity // this imports ReactiveMethodSecurityConfiguration
|
||||
static class WithRolePrefixConfiguration {
|
||||
|
||||
@Bean
|
||||
GrantedAuthorityDefaults grantedAuthorityDefaults() {
|
||||
return new GrantedAuthorityDefaults("CUSTOM_");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void rolePrefixWithGrantedAuthorityDefaultsAndSubclassWithProxyingEnabled() throws NoSuchMethodException {
|
||||
this.spring.register(SubclassConfig.class).autowire();
|
||||
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken(
|
||||
"principal", "credential", "ROLE_ABC");
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("principal", "credential",
|
||||
"ROLE_ABC");
|
||||
MockMethodInvocation methodInvocation = new MockMethodInvocation(new Foo(), Foo.class, "bar", String.class);
|
||||
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler
|
||||
.createEvaluationContext(authentication, methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject()
|
||||
.getValue();
|
||||
EvaluationContext context = this.methodSecurityExpressionHandler.createEvaluationContext(authentication,
|
||||
methodInvocation);
|
||||
SecurityExpressionRoot root = (SecurityExpressionRoot) context.getRootObject().getValue();
|
||||
|
||||
assertThat(root.hasRole("ROLE_ABC")).isTrue();
|
||||
assertThat(root.hasRole("ABC")).isTrue();
|
||||
@@ -106,10 +105,14 @@ public class ReactiveMethodSecurityConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
static class SubclassConfig extends ReactiveMethodSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
private static class Foo {
|
||||
public void bar(String param){
|
||||
|
||||
public void bar(String param) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -42,6 +42,7 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
*
|
||||
*/
|
||||
public class SampleEnableGlobalMethodSecurityTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -50,8 +51,8 @@ public class SampleEnableGlobalMethodSecurityTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
SecurityContextHolder.getContext().setAuthentication(
|
||||
new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
SecurityContextHolder.getContext()
|
||||
.setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -61,12 +62,12 @@ public class SampleEnableGlobalMethodSecurityTests {
|
||||
assertThat(this.methodSecurityService.secured()).isNull();
|
||||
assertThat(this.methodSecurityService.jsr250()).isNull();
|
||||
|
||||
assertThatThrownBy(() -> this.methodSecurityService.preAuthorize())
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
assertThatThrownBy(() -> this.methodSecurityService.preAuthorize()).isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled=true)
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
static class SampleWebSecurityConfig {
|
||||
|
||||
@Bean
|
||||
public MethodSecurityService methodSecurityService() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -81,8 +82,8 @@ public class SampleEnableGlobalMethodSecurityTests {
|
||||
.withUser("admin").password("password").roles("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void customPermissionHandler() {
|
||||
@@ -91,12 +92,12 @@ public class SampleEnableGlobalMethodSecurityTests {
|
||||
assertThat(this.methodSecurityService.hasPermission("allowed")).isNull();
|
||||
|
||||
assertThatThrownBy(() -> this.methodSecurityService.hasPermission("denied"))
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
.isInstanceOf(AccessDeniedException.class);
|
||||
}
|
||||
|
||||
|
||||
@EnableGlobalMethodSecurity(prePostEnabled=true)
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
public static class CustomPermissionEvaluatorWebSecurityConfig extends GlobalMethodSecurityConfiguration {
|
||||
|
||||
@Bean
|
||||
public MethodSecurityService methodSecurityService() {
|
||||
return new MethodSecurityServiceImpl();
|
||||
@@ -118,18 +119,20 @@ public class SampleEnableGlobalMethodSecurityTests {
|
||||
.withUser("admin").password("password").roles("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class CustomPermissionEvaluator implements PermissionEvaluator {
|
||||
public boolean hasPermission(Authentication authentication,
|
||||
Object targetDomainObject, Object permission) {
|
||||
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject, Object permission) {
|
||||
return !"denied".equals(targetDomainObject);
|
||||
}
|
||||
|
||||
public boolean hasPermission(Authentication authentication,
|
||||
Serializable targetId, String targetType, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Serializable targetId, String targetType,
|
||||
Object permission) {
|
||||
return !"denied".equals(targetId);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -77,21 +77,23 @@ public class Sec2758Tests {
|
||||
|
||||
this.spring.register(SecurityConfig.class).autowire();
|
||||
|
||||
assertThatCode(() -> service.doJsr250())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> service.doJsr250()).doesNotThrowAnyException();
|
||||
|
||||
assertThatCode(() -> service.doPreAuthorize())
|
||||
.doesNotThrowAnyException();
|
||||
assertThatCode(() -> service.doPreAuthorize()).doesNotThrowAnyException();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableGlobalMethodSecurity(prePostEnabled=true, jsr250Enabled = true)
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true, jsr250Enabled = true)
|
||||
static class SecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@RestController
|
||||
static class RootController {
|
||||
|
||||
@GetMapping("/")
|
||||
public String ok() { return "ok"; }
|
||||
public String ok() {
|
||||
return "ok";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -116,11 +118,15 @@ public class Sec2758Tests {
|
||||
}
|
||||
|
||||
static class Service {
|
||||
|
||||
@PreAuthorize("hasRole('CUSTOM')")
|
||||
public void doPreAuthorize() {}
|
||||
public void doPreAuthorize() {
|
||||
}
|
||||
|
||||
@RolesAllowed("CUSTOM")
|
||||
public void doJsr250() {}
|
||||
public void doJsr250() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class DefaultRolesPrefixPostProcessor implements BeanPostProcessor, PriorityOrdered {
|
||||
@@ -148,5 +154,7 @@ public class Sec2758Tests {
|
||||
public int getOrder() {
|
||||
return PriorityOrdered.HIGHEST_PRECEDENCE;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -34,6 +34,7 @@ import static org.mockito.Mockito.verify;
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class AbstractConfiguredSecurityBuilderTests {
|
||||
|
||||
private TestConfiguredSecurityBuilder builder;
|
||||
|
||||
@Before
|
||||
@@ -80,7 +81,8 @@ public class AbstractConfiguredSecurityBuilderTests {
|
||||
|
||||
@Test(expected = IllegalStateException.class)
|
||||
public void getConfigurerWhenMultipleConfigurersThenThrowIllegalStateException() throws Exception {
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class), true);
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class),
|
||||
true);
|
||||
builder.apply(new DelegateSecurityConfigurer());
|
||||
builder.apply(new DelegateSecurityConfigurer());
|
||||
builder.getConfigurer(DelegateSecurityConfigurer.class);
|
||||
@@ -88,7 +90,8 @@ public class AbstractConfiguredSecurityBuilderTests {
|
||||
|
||||
@Test(expected = IllegalStateException.class)
|
||||
public void removeConfigurerWhenMultipleConfigurersThenThrowIllegalStateException() throws Exception {
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class), true);
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class),
|
||||
true);
|
||||
builder.apply(new DelegateSecurityConfigurer());
|
||||
builder.apply(new DelegateSecurityConfigurer());
|
||||
builder.removeConfigurer(DelegateSecurityConfigurer.class);
|
||||
@@ -98,10 +101,12 @@ public class AbstractConfiguredSecurityBuilderTests {
|
||||
public void removeConfigurersWhenMultipleConfigurersThenConfigurersRemoved() throws Exception {
|
||||
DelegateSecurityConfigurer configurer1 = new DelegateSecurityConfigurer();
|
||||
DelegateSecurityConfigurer configurer2 = new DelegateSecurityConfigurer();
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class), true);
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class),
|
||||
true);
|
||||
builder.apply(configurer1);
|
||||
builder.apply(configurer2);
|
||||
List<DelegateSecurityConfigurer> removedConfigurers = builder.removeConfigurers(DelegateSecurityConfigurer.class);
|
||||
List<DelegateSecurityConfigurer> removedConfigurers = builder
|
||||
.removeConfigurers(DelegateSecurityConfigurer.class);
|
||||
assertThat(removedConfigurers).hasSize(2);
|
||||
assertThat(removedConfigurers).containsExactly(configurer1, configurer2);
|
||||
assertThat(builder.getConfigurers(DelegateSecurityConfigurer.class)).isEmpty();
|
||||
@@ -111,7 +116,8 @@ public class AbstractConfiguredSecurityBuilderTests {
|
||||
public void getConfigurersWhenMultipleConfigurersThenConfigurersReturned() throws Exception {
|
||||
DelegateSecurityConfigurer configurer1 = new DelegateSecurityConfigurer();
|
||||
DelegateSecurityConfigurer configurer2 = new DelegateSecurityConfigurer();
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class), true);
|
||||
TestConfiguredSecurityBuilder builder = new TestConfiguredSecurityBuilder(mock(ObjectPostProcessor.class),
|
||||
true);
|
||||
builder.apply(configurer1);
|
||||
builder.apply(configurer2);
|
||||
List<DelegateSecurityConfigurer> configurers = builder.getConfigurers(DelegateSecurityConfigurer.class);
|
||||
@@ -120,29 +126,39 @@ public class AbstractConfiguredSecurityBuilderTests {
|
||||
assertThat(builder.getConfigurers(DelegateSecurityConfigurer.class)).hasSize(2);
|
||||
}
|
||||
|
||||
private static class DelegateSecurityConfigurer extends SecurityConfigurerAdapter<Object, TestConfiguredSecurityBuilder> {
|
||||
private static class DelegateSecurityConfigurer
|
||||
extends SecurityConfigurerAdapter<Object, TestConfiguredSecurityBuilder> {
|
||||
|
||||
private static SecurityConfigurer<Object, TestConfiguredSecurityBuilder> CONFIGURER;
|
||||
|
||||
@Override
|
||||
public void init(TestConfiguredSecurityBuilder builder) throws Exception {
|
||||
builder.apply(CONFIGURER);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private static class TestSecurityConfigurer extends SecurityConfigurerAdapter<Object, TestConfiguredSecurityBuilder> { }
|
||||
private static class TestSecurityConfigurer
|
||||
extends SecurityConfigurerAdapter<Object, TestConfiguredSecurityBuilder> {
|
||||
|
||||
private static class TestConfiguredSecurityBuilder extends AbstractConfiguredSecurityBuilder<Object, TestConfiguredSecurityBuilder> {
|
||||
}
|
||||
|
||||
private static class TestConfiguredSecurityBuilder
|
||||
extends AbstractConfiguredSecurityBuilder<Object, TestConfiguredSecurityBuilder> {
|
||||
|
||||
private TestConfiguredSecurityBuilder(ObjectPostProcessor<Object> objectPostProcessor) {
|
||||
super(objectPostProcessor);
|
||||
}
|
||||
|
||||
private TestConfiguredSecurityBuilder(ObjectPostProcessor<Object> objectPostProcessor, boolean allowConfigurersOfSameType) {
|
||||
private TestConfiguredSecurityBuilder(ObjectPostProcessor<Object> objectPostProcessor,
|
||||
boolean allowConfigurersOfSameType) {
|
||||
super(objectPostProcessor, allowConfigurersOfSameType);
|
||||
}
|
||||
|
||||
public Object performBuild() {
|
||||
return "success";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -30,10 +30,11 @@ import org.springframework.web.context.support.AnnotationConfigWebApplicationCon
|
||||
*
|
||||
* @author Ankur Pathak
|
||||
*/
|
||||
public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
public class AbstractRequestMatcherRegistryAnyMatcherTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AntMatchersAfterAnyRequestConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -43,15 +44,17 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BeanCreationException.class)
|
||||
public void antMatchersCanNotWorkAfterAnyRequest(){
|
||||
public void antMatchersCanNotWorkAfterAnyRequest() {
|
||||
loadConfig(AntMatchersAfterAnyRequestConfig.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class MvcMatchersAfterAnyRequestConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -61,6 +64,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BeanCreationException.class)
|
||||
@@ -70,6 +74,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RegexMatchersAfterAnyRequestConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -79,6 +84,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BeanCreationException.class)
|
||||
@@ -88,6 +94,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnyRequestAfterItselfConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -97,6 +104,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BeanCreationException.class)
|
||||
@@ -106,6 +114,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatchersAfterAnyRequestConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -115,6 +124,7 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = BeanCreationException.class)
|
||||
@@ -129,4 +139,5 @@ public class AbstractRequestMatcherRegistryAnyMatcherTests{
|
||||
context.setServletContext(new MockServletContext());
|
||||
context.refresh();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -32,6 +32,7 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class AbstractRequestMatcherRegistryTests {
|
||||
|
||||
private TestRequestMatcherRegistry matcherRegistry;
|
||||
|
||||
@Before
|
||||
@@ -87,5 +88,7 @@ public class AbstractRequestMatcherRegistryTests {
|
||||
protected List<RequestMatcher> chainRequestMatchers(List<RequestMatcher> requestMatchers) {
|
||||
return requestMatchers;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -41,7 +41,6 @@ import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry
|
||||
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*
|
||||
*/
|
||||
@@ -49,8 +48,10 @@ import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class HttpSecurityHeadersTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext wac;
|
||||
|
||||
@Autowired
|
||||
Filter springSecurityFilterChain;
|
||||
|
||||
@@ -58,44 +59,46 @@ public class HttpSecurityHeadersTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mockMvc = MockMvcBuilders
|
||||
.webAppContextSetup(wac)
|
||||
.addFilters(springSecurityFilterChain)
|
||||
.build();
|
||||
mockMvc = MockMvcBuilders.webAppContextSetup(wac).addFilters(springSecurityFilterChain).build();
|
||||
}
|
||||
|
||||
// gh-2953
|
||||
// gh-3975
|
||||
@Test
|
||||
public void headerWhenSpringMvcResourceThenCacheRelatedHeadersReset() throws Exception {
|
||||
mockMvc.perform(get("/resources/file.js"))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "max-age=12345"))
|
||||
.andExpect(header().doesNotExist(HttpHeaders.PRAGMA))
|
||||
.andExpect(header().doesNotExist(HttpHeaders.EXPIRES));
|
||||
mockMvc.perform(get("/resources/file.js")).andExpect(status().isOk())
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "max-age=12345"))
|
||||
.andExpect(header().doesNotExist(HttpHeaders.PRAGMA))
|
||||
.andExpect(header().doesNotExist(HttpHeaders.EXPIRES));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void headerWhenNotSpringResourceThenCacheRelatedHeadersSet() throws Exception {
|
||||
mockMvc.perform(get("/notresource"))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"));
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebMvc
|
||||
@Configuration
|
||||
static class WebMvcConfig implements WebMvcConfigurer {
|
||||
|
||||
@Override
|
||||
public void addResourceHandlers(ResourceHandlerRegistry registry) {
|
||||
registry.addResourceHandler("/resources/**").addResourceLocations("classpath:/resources/").setCachePeriod(12345);
|
||||
registry.addResourceHandler("/resources/**").addResourceLocations("classpath:/resources/")
|
||||
.setCachePeriod(12345);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -48,6 +48,7 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class SampleWebSecurityConfigurerAdapterTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -55,7 +56,9 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
private FilterChainProxy springSecurityFilterChain;
|
||||
|
||||
private MockHttpServletRequest request;
|
||||
|
||||
private MockHttpServletResponse response;
|
||||
|
||||
private MockFilterChain chain;
|
||||
|
||||
@Before
|
||||
@@ -129,10 +132,12 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
* </authentication-provider>
|
||||
* </authentication-manager>
|
||||
* </code>
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
@EnableWebSecurity
|
||||
public static class HelloWorldWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -141,8 +146,8 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void readmeSampleWhenRequestSecureResourceThenRedirectToLogin() throws Exception {
|
||||
@@ -201,11 +206,13 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
* <authentication-provider>
|
||||
* <user-service>
|
||||
* <user username="user" password="password" authorities="ROLE_USER"/>
|
||||
* <user username="admin" password="password" authorities="ROLE_USER,ROLE_ADMIN"/>
|
||||
* <user username="admin" password="password" authorities=
|
||||
"ROLE_USER,ROLE_ADMIN"/>
|
||||
* </user-service>
|
||||
* </authentication-provider>
|
||||
* </authentication-manager>
|
||||
* </code>
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
@EnableWebSecurity
|
||||
@@ -213,9 +220,7 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web
|
||||
.ignoring()
|
||||
.antMatchers("/resources/**");
|
||||
web.ignoring().antMatchers("/resources/**");
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -242,8 +247,8 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
.withUser(PasswordEncodedUser.admin());
|
||||
// @formatter:on
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void multiHttpSampleWhenRequestSecureResourceThenRedirectToLogin() throws Exception {
|
||||
@@ -293,7 +298,8 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
this.spring.register(SampleMultiHttpSecurityConfig.class).autowire();
|
||||
|
||||
this.request.setServletPath("/api/admin/test");
|
||||
this.request.addHeader("Authorization", "Basic " + Base64.getEncoder().encodeToString("user:password".getBytes()));
|
||||
this.request.addHeader("Authorization",
|
||||
"Basic " + Base64.getEncoder().encodeToString("user:password".getBytes()));
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_FORBIDDEN);
|
||||
@@ -304,7 +310,8 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
this.spring.register(SampleMultiHttpSecurityConfig.class).autowire();
|
||||
|
||||
this.request.setServletPath("/api/admin/test");
|
||||
this.request.addHeader("Authorization", "Basic " + Base64.getEncoder().encodeToString("admin:password".getBytes()));
|
||||
this.request.addHeader("Authorization",
|
||||
"Basic " + Base64.getEncoder().encodeToString("admin:password".getBytes()));
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_OK);
|
||||
@@ -339,15 +346,18 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
* <authentication-provider>
|
||||
* <user-service>
|
||||
* <user username="user" password="password" authorities="ROLE_USER"/>
|
||||
* <user username="admin" password="password" authorities="ROLE_USER,ROLE_ADMIN"/>
|
||||
* <user username="admin" password="password" authorities=
|
||||
"ROLE_USER,ROLE_ADMIN"/>
|
||||
* </user-service>
|
||||
* </authentication-provider>
|
||||
* </authentication-manager>
|
||||
* </code>
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
@EnableWebSecurity
|
||||
public static class SampleMultiHttpSecurityConfig {
|
||||
|
||||
@Autowired
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -361,6 +371,7 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
@Configuration
|
||||
@Order(1)
|
||||
public static class ApiWebSecurityConfigurationAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -372,15 +383,15 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
.httpBasic();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
public static class FormLoginWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web
|
||||
.ignoring()
|
||||
.antMatchers("/resources/**");
|
||||
web.ignoring().antMatchers("/resources/**");
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -396,6 +407,9 @@ public class SampleWebSecurityConfigurerAdapterTests {
|
||||
.permitAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -53,14 +53,15 @@ import static org.powermock.api.mockito.PowerMockito.when;
|
||||
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*
|
||||
*/
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareForTest({ SpringFactoriesLoader.class, WebAsyncManager.class })
|
||||
@PowerMockIgnore({ "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*", "javax.xml.transform.*" })
|
||||
@PowerMockIgnore({ "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*",
|
||||
"javax.xml.transform.*" })
|
||||
public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
|
||||
ConfigurableWebApplicationContext context;
|
||||
|
||||
@Rule
|
||||
@@ -80,9 +81,8 @@ public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
public void loadConfigWhenDefaultConfigurerAsSpringFactoryhenDefaultConfigurerApplied() {
|
||||
spy(SpringFactoriesLoader.class);
|
||||
DefaultConfigurer configurer = new DefaultConfigurer();
|
||||
when(SpringFactoriesLoader
|
||||
.loadFactories(AbstractHttpConfigurer.class, getClass().getClassLoader()))
|
||||
.thenReturn(Arrays.<AbstractHttpConfigurer>asList(configurer));
|
||||
when(SpringFactoriesLoader.loadFactories(AbstractHttpConfigurer.class, getClass().getClassLoader()))
|
||||
.thenReturn(Arrays.<AbstractHttpConfigurer>asList(configurer));
|
||||
|
||||
loadConfig(Config.class);
|
||||
|
||||
@@ -100,13 +100,17 @@ public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class Config extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class DefaultConfigurer extends AbstractHttpConfigurer<DefaultConfigurer, HttpSecurity> {
|
||||
|
||||
boolean init;
|
||||
|
||||
boolean configure;
|
||||
|
||||
@Override
|
||||
@@ -118,6 +122,7 @@ public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
public void configure(HttpSecurity builder) {
|
||||
this.configure = true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -128,15 +133,15 @@ public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
|
||||
this.mockMvc.perform(get("/").requestAttr(WebAsyncUtils.WEB_ASYNC_MANAGER_ATTRIBUTE, webAsyncManager));
|
||||
|
||||
ArgumentCaptor<CallableProcessingInterceptor> callableProcessingInterceptorArgCaptor =
|
||||
ArgumentCaptor.forClass(CallableProcessingInterceptor.class);
|
||||
verify(webAsyncManager, atLeastOnce()).registerCallableInterceptor(any(), callableProcessingInterceptorArgCaptor.capture());
|
||||
ArgumentCaptor<CallableProcessingInterceptor> callableProcessingInterceptorArgCaptor = ArgumentCaptor
|
||||
.forClass(CallableProcessingInterceptor.class);
|
||||
verify(webAsyncManager, atLeastOnce()).registerCallableInterceptor(any(),
|
||||
callableProcessingInterceptorArgCaptor.capture());
|
||||
|
||||
CallableProcessingInterceptor callableProcessingInterceptor =
|
||||
callableProcessingInterceptorArgCaptor.getAllValues().stream()
|
||||
.filter(e -> SecurityContextCallableProcessingInterceptor.class.isAssignableFrom(e.getClass()))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
CallableProcessingInterceptor callableProcessingInterceptor = callableProcessingInterceptorArgCaptor
|
||||
.getAllValues().stream()
|
||||
.filter(e -> SecurityContextCallableProcessingInterceptor.class.isAssignableFrom(e.getClass()))
|
||||
.findFirst().orElse(null);
|
||||
|
||||
assertThat(callableProcessingInterceptor).isNotNull();
|
||||
}
|
||||
@@ -156,5 +161,7 @@ public class WebSecurityConfigurerAdapterPowermockTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -71,6 +71,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class WebSecurityConfigurerAdapterTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -81,14 +82,12 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public void loadConfigWhenRequestSecureThenDefaultSecurityHeadersReturned() throws Exception {
|
||||
this.spring.register(HeadersArePopulatedByDefaultConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("X-Content-Type-Options", "nosniff"))
|
||||
.andExpect(header().string("X-Frame-Options", "DENY"))
|
||||
.andExpect(header().string("Strict-Transport-Security", "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string("Cache-Control", "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string("Pragma", "no-cache"))
|
||||
.andExpect(header().string("Expires", "0"))
|
||||
.andExpect(header().string("X-XSS-Protection", "1; mode=block"));
|
||||
this.mockMvc.perform(get("/").secure(true)).andExpect(header().string("X-Content-Type-Options", "nosniff"))
|
||||
.andExpect(header().string("X-Frame-Options", "DENY"))
|
||||
.andExpect(header().string("Strict-Transport-Security", "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string("Cache-Control", "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string("Pragma", "no-cache")).andExpect(header().string("Expires", "0"))
|
||||
.andExpect(header().string("X-XSS-Protection", "1; mode=block"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -106,14 +105,14 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenRequestAuthenticateThenAuthenticationEventPublished() throws Exception {
|
||||
this.spring.register(InMemoryAuthWithWebSecurityConfigurerAdapter.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(status().is3xxRedirection());
|
||||
this.mockMvc.perform(formLogin()).andExpect(status().is3xxRedirection());
|
||||
|
||||
assertThat(InMemoryAuthWithWebSecurityConfigurerAdapter.EVENTS).isNotEmpty();
|
||||
assertThat(InMemoryAuthWithWebSecurityConfigurerAdapter.EVENTS).hasSize(1);
|
||||
@@ -121,7 +120,7 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InMemoryAuthWithWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter
|
||||
implements ApplicationListener<AuthenticationSuccessEvent> {
|
||||
implements ApplicationListener<AuthenticationSuccessEvent> {
|
||||
|
||||
static List<AuthenticationSuccessEvent> EVENTS = new ArrayList<>();
|
||||
|
||||
@@ -138,22 +137,22 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public void onApplicationEvent(AuthenticationSuccessEvent event) {
|
||||
EVENTS.add(event);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenInMemoryConfigureProtectedThenPasswordUpgraded() throws Exception {
|
||||
this.spring.register(InMemoryConfigureProtectedConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(status().is3xxRedirection());
|
||||
this.mockMvc.perform(formLogin()).andExpect(status().is3xxRedirection());
|
||||
|
||||
UserDetailsService uds = this.spring.getContext()
|
||||
.getBean(UserDetailsService.class);
|
||||
UserDetailsService uds = this.spring.getContext().getBean(UserDetailsService.class);
|
||||
assertThat(uds.loadUserByUsername("user").getPassword()).startsWith("{bcrypt}");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InMemoryConfigureProtectedConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -168,22 +167,22 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public UserDetailsService userDetailsServiceBean() throws Exception {
|
||||
return super.userDetailsServiceBean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenInMemoryConfigureGlobalThenPasswordUpgraded() throws Exception {
|
||||
this.spring.register(InMemoryConfigureGlobalConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(status().is3xxRedirection());
|
||||
this.mockMvc.perform(formLogin()).andExpect(status().is3xxRedirection());
|
||||
|
||||
UserDetailsService uds = this.spring.getContext()
|
||||
.getBean(UserDetailsService.class);
|
||||
UserDetailsService uds = this.spring.getContext().getBean(UserDetailsService.class);
|
||||
assertThat(uds.loadUserByUsername("user").getPassword()).startsWith("{bcrypt}");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InMemoryConfigureGlobalConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -198,24 +197,28 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public UserDetailsService userDetailsServiceBean() throws Exception {
|
||||
return super.userDetailsServiceBean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenCustomContentNegotiationStrategyBeanThenOverridesDefault() {
|
||||
OverrideContentNegotiationStrategySharedObjectConfig.CONTENT_NEGOTIATION_STRATEGY_BEAN = mock(ContentNegotiationStrategy.class);
|
||||
OverrideContentNegotiationStrategySharedObjectConfig.CONTENT_NEGOTIATION_STRATEGY_BEAN = mock(
|
||||
ContentNegotiationStrategy.class);
|
||||
this.spring.register(OverrideContentNegotiationStrategySharedObjectConfig.class).autowire();
|
||||
|
||||
OverrideContentNegotiationStrategySharedObjectConfig securityConfig =
|
||||
this.spring.getContext().getBean(OverrideContentNegotiationStrategySharedObjectConfig.class);
|
||||
OverrideContentNegotiationStrategySharedObjectConfig securityConfig = this.spring.getContext()
|
||||
.getBean(OverrideContentNegotiationStrategySharedObjectConfig.class);
|
||||
|
||||
assertThat(securityConfig.contentNegotiationStrategySharedObject).isNotNull();
|
||||
assertThat(securityConfig.contentNegotiationStrategySharedObject)
|
||||
.isSameAs(OverrideContentNegotiationStrategySharedObjectConfig.CONTENT_NEGOTIATION_STRATEGY_BEAN);
|
||||
.isSameAs(OverrideContentNegotiationStrategySharedObjectConfig.CONTENT_NEGOTIATION_STRATEGY_BEAN);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class OverrideContentNegotiationStrategySharedObjectConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ContentNegotiationStrategy CONTENT_NEGOTIATION_STRATEGY_BEAN;
|
||||
|
||||
private ContentNegotiationStrategy contentNegotiationStrategySharedObject;
|
||||
|
||||
@Bean
|
||||
@@ -228,21 +231,24 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
this.contentNegotiationStrategySharedObject = http.getSharedObject(ContentNegotiationStrategy.class);
|
||||
super.configure(http);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenDefaultContentNegotiationStrategyThenHeaderContentNegotiationStrategy() {
|
||||
this.spring.register(ContentNegotiationStrategyDefaultSharedObjectConfig.class).autowire();
|
||||
|
||||
ContentNegotiationStrategyDefaultSharedObjectConfig securityConfig =
|
||||
this.spring.getContext().getBean(ContentNegotiationStrategyDefaultSharedObjectConfig.class);
|
||||
ContentNegotiationStrategyDefaultSharedObjectConfig securityConfig = this.spring.getContext()
|
||||
.getBean(ContentNegotiationStrategyDefaultSharedObjectConfig.class);
|
||||
|
||||
assertThat(securityConfig.contentNegotiationStrategySharedObject).isNotNull();
|
||||
assertThat(securityConfig.contentNegotiationStrategySharedObject).isInstanceOf(HeaderContentNegotiationStrategy.class);
|
||||
assertThat(securityConfig.contentNegotiationStrategySharedObject)
|
||||
.isInstanceOf(HeaderContentNegotiationStrategy.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ContentNegotiationStrategyDefaultSharedObjectConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
private ContentNegotiationStrategy contentNegotiationStrategySharedObject;
|
||||
|
||||
@Override
|
||||
@@ -250,6 +256,7 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
this.contentNegotiationStrategySharedObject = http.getSharedObject(ContentNegotiationStrategy.class);
|
||||
super.configure(http);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -258,23 +265,26 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
|
||||
MyFilter myFilter = this.spring.getContext().getBean(MyFilter.class);
|
||||
|
||||
Throwable thrown = catchThrowable(() -> myFilter.userDetailsService.loadUserByUsername("user") );
|
||||
Throwable thrown = catchThrowable(() -> myFilter.userDetailsService.loadUserByUsername("user"));
|
||||
assertThat(thrown).isNull();
|
||||
|
||||
thrown = catchThrowable(() -> myFilter.userDetailsService.loadUserByUsername("admin") );
|
||||
thrown = catchThrowable(() -> myFilter.userDetailsService.loadUserByUsername("admin"));
|
||||
assertThat(thrown).isInstanceOf(UsernameNotFoundException.class);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class RequiresUserDetailsServiceConfig {
|
||||
|
||||
@Bean
|
||||
public MyFilter myFilter(UserDetailsService userDetailsService) {
|
||||
return new MyFilter(userDetailsService);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class UserDetailsServiceConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
private MyFilter myFilter;
|
||||
|
||||
@@ -297,9 +307,11 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class MyFilter extends OncePerRequestFilter {
|
||||
|
||||
private UserDetailsService userDetailsService;
|
||||
|
||||
MyFilter(UserDetailsService userDetailsService) {
|
||||
@@ -307,11 +319,11 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doFilterInternal(HttpServletRequest request,
|
||||
HttpServletResponse response,
|
||||
FilterChain filterChain) throws ServletException, IOException {
|
||||
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
|
||||
FilterChain filterChain) throws ServletException, IOException {
|
||||
filterChain.doFilter(request, response);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2274: WebSecurityConfigurer adds ApplicationContext as a shared object
|
||||
@@ -319,8 +331,8 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public void loadConfigWhenSharedObjectsCreatedThenApplicationContextAdded() {
|
||||
this.spring.register(ApplicationContextSharedObjectConfig.class).autowire();
|
||||
|
||||
ApplicationContextSharedObjectConfig securityConfig =
|
||||
this.spring.getContext().getBean(ApplicationContextSharedObjectConfig.class);
|
||||
ApplicationContextSharedObjectConfig securityConfig = this.spring.getContext()
|
||||
.getBean(ApplicationContextSharedObjectConfig.class);
|
||||
|
||||
assertThat(securityConfig.applicationContextSharedObject).isNotNull();
|
||||
assertThat(securityConfig.applicationContextSharedObject).isSameAs(this.spring.getContext());
|
||||
@@ -328,6 +340,7 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ApplicationContextSharedObjectConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
private ApplicationContext applicationContextSharedObject;
|
||||
|
||||
@Override
|
||||
@@ -335,6 +348,7 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
this.applicationContextSharedObject = http.getSharedObject(ApplicationContext.class);
|
||||
super.configure(http);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -342,17 +356,18 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
CustomTrustResolverConfig.AUTHENTICATION_TRUST_RESOLVER_BEAN = mock(AuthenticationTrustResolver.class);
|
||||
this.spring.register(CustomTrustResolverConfig.class).autowire();
|
||||
|
||||
CustomTrustResolverConfig securityConfig =
|
||||
this.spring.getContext().getBean(CustomTrustResolverConfig.class);
|
||||
CustomTrustResolverConfig securityConfig = this.spring.getContext().getBean(CustomTrustResolverConfig.class);
|
||||
|
||||
assertThat(securityConfig.authenticationTrustResolverSharedObject).isNotNull();
|
||||
assertThat(securityConfig.authenticationTrustResolverSharedObject)
|
||||
.isSameAs(CustomTrustResolverConfig.AUTHENTICATION_TRUST_RESOLVER_BEAN);
|
||||
.isSameAs(CustomTrustResolverConfig.AUTHENTICATION_TRUST_RESOLVER_BEAN);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomTrustResolverConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationTrustResolver AUTHENTICATION_TRUST_RESOLVER_BEAN;
|
||||
|
||||
private AuthenticationTrustResolver authenticationTrustResolverSharedObject;
|
||||
|
||||
@Bean
|
||||
@@ -365,21 +380,23 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
this.authenticationTrustResolverSharedObject = http.getSharedObject(AuthenticationTrustResolver.class);
|
||||
super.configure(http);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void compareOrderWebSecurityConfigurerAdapterWhenLowestOrderToDefaultOrderThenGreaterThanZero() {
|
||||
AnnotationAwareOrderComparator comparator = new AnnotationAwareOrderComparator();
|
||||
assertThat(comparator.compare(
|
||||
new LowestPriorityWebSecurityConfig(),
|
||||
new DefaultOrderWebSecurityConfig())).isGreaterThan(0);
|
||||
assertThat(comparator.compare(new LowestPriorityWebSecurityConfig(), new DefaultOrderWebSecurityConfig()))
|
||||
.isGreaterThan(0);
|
||||
}
|
||||
|
||||
static class DefaultOrderWebSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Order
|
||||
static class LowestPriorityWebSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
// gh-7515
|
||||
@@ -387,17 +404,17 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public void performWhenUsingAuthenticationEventPublisherBeanThenUses() throws Exception {
|
||||
this.spring.register(CustomAuthenticationEventPublisherBean.class).autowire();
|
||||
|
||||
AuthenticationEventPublisher authenticationEventPublisher =
|
||||
this.spring.getContext().getBean(AuthenticationEventPublisher.class);
|
||||
AuthenticationEventPublisher authenticationEventPublisher = this.spring.getContext()
|
||||
.getBean(AuthenticationEventPublisher.class);
|
||||
|
||||
this.mockMvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")));
|
||||
this.mockMvc.perform(get("/").with(httpBasic("user", "password")));
|
||||
|
||||
verify(authenticationEventPublisher).publishAuthenticationSuccess(any(Authentication.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomAuthenticationEventPublisherBean extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Bean
|
||||
@Override
|
||||
public UserDetailsService userDetailsService() {
|
||||
@@ -408,6 +425,7 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public AuthenticationEventPublisher authenticationEventPublisher() {
|
||||
return mock(AuthenticationEventPublisher.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-4400
|
||||
@@ -415,24 +433,27 @@ public class WebSecurityConfigurerAdapterTests {
|
||||
public void performWhenUsingAuthenticationEventPublisherInDslThenUses() throws Exception {
|
||||
this.spring.register(CustomAuthenticationEventPublisherDsl.class).autowire();
|
||||
|
||||
AuthenticationEventPublisher authenticationEventPublisher =
|
||||
CustomAuthenticationEventPublisherDsl.EVENT_PUBLISHER;
|
||||
AuthenticationEventPublisher authenticationEventPublisher = CustomAuthenticationEventPublisherDsl.EVENT_PUBLISHER;
|
||||
|
||||
this.mockMvc.perform(get("/")
|
||||
.with(httpBasic("user", "password"))); // fails since no providers configured
|
||||
this.mockMvc.perform(get("/").with(httpBasic("user", "password"))); // fails since
|
||||
// no
|
||||
// providers
|
||||
// configured
|
||||
|
||||
verify(authenticationEventPublisher).publishAuthenticationFailure(
|
||||
any(AuthenticationException.class),
|
||||
verify(authenticationEventPublisher).publishAuthenticationFailure(any(AuthenticationException.class),
|
||||
any(Authentication.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomAuthenticationEventPublisherDsl extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationEventPublisher EVENT_PUBLISHER = mock(AuthenticationEventPublisher.class);
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.authenticationEventPublisher(EVENT_PUBLISHER);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -49,6 +49,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class HttpConfigurationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -57,11 +58,11 @@ public class HttpConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void configureWhenAddFilterUnregisteredThenThrowsBeanCreationException() {
|
||||
Throwable thrown = catchThrowable(() -> this.spring.register(UnregisteredFilterConfig.class).autowire() );
|
||||
Throwable thrown = catchThrowable(() -> this.spring.register(UnregisteredFilterConfig.class).autowire());
|
||||
assertThat(thrown).isInstanceOf(BeanCreationException.class);
|
||||
assertThat(thrown.getMessage()).contains("The Filter class " + UnregisteredFilter.class.getName() +
|
||||
" does not have a registered order and cannot be added without a specified order." +
|
||||
" Consider using addFilterBefore or addFilterAfter instead.");
|
||||
assertThat(thrown.getMessage()).contains("The Filter class " + UnregisteredFilter.class.getName()
|
||||
+ " does not have a registered order and cannot be added without a specified order."
|
||||
+ " Consider using addFilterBefore or addFilterAfter instead.");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -81,15 +82,17 @@ public class HttpConfigurationTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class UnregisteredFilter extends OncePerRequestFilter {
|
||||
|
||||
@Override
|
||||
protected void doFilterInternal(HttpServletRequest request,
|
||||
HttpServletResponse response,
|
||||
FilterChain filterChain) throws ServletException, IOException {
|
||||
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
|
||||
FilterChain filterChain) throws ServletException, IOException {
|
||||
filterChain.doFilter(request, response);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// https://github.com/spring-projects/spring-security-javaconfig/issues/104
|
||||
@@ -100,12 +103,13 @@ public class HttpConfigurationTests {
|
||||
|
||||
this.mockMvc.perform(get("/"));
|
||||
|
||||
verify(CasAuthenticationFilterConfig.CAS_AUTHENTICATION_FILTER).doFilter(
|
||||
any(ServletRequest.class), any(ServletResponse.class), any(FilterChain.class));
|
||||
verify(CasAuthenticationFilterConfig.CAS_AUTHENTICATION_FILTER).doFilter(any(ServletRequest.class),
|
||||
any(ServletResponse.class), any(FilterChain.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CasAuthenticationFilterConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CasAuthenticationFilter CAS_AUTHENTICATION_FILTER;
|
||||
|
||||
protected void configure(HttpSecurity http) {
|
||||
@@ -114,6 +118,7 @@ public class HttpConfigurationTests {
|
||||
.addFilter(CAS_AUTHENTICATION_FILTER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -128,6 +133,7 @@ public class HttpConfigurationTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherRegistryConfigs extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -142,5 +148,7 @@ public class HttpConfigurationTests {
|
||||
.httpBasic();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -63,33 +63,38 @@ import static org.springframework.test.web.servlet.request.MockMvcRequestBuilder
|
||||
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;
|
||||
|
||||
/**
|
||||
* Tests to verify that all the functionality of <http> attributes are present in Java Config.
|
||||
* Tests to verify that all the functionality of <http> attributes are present in Java
|
||||
* Config.
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class NamespaceHttpTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@Autowired
|
||||
private MockMvc mockMvc;
|
||||
|
||||
@Test // http@access-decision-manager-ref
|
||||
@Test // http@access-decision-manager-ref
|
||||
public void configureWhenAccessDecisionManagerSetThenVerifyUse() throws Exception {
|
||||
AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER = mock(AccessDecisionManager.class);
|
||||
when(AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER.supports(FilterInvocation.class)).thenReturn(true);
|
||||
when(AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER.supports(any(ConfigAttribute.class))).thenReturn(true);
|
||||
when(AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER.supports(any(ConfigAttribute.class)))
|
||||
.thenReturn(true);
|
||||
|
||||
this.spring.register(AccessDecisionManagerRefConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"));
|
||||
|
||||
verify(AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER, times(1)).decide(any(Authentication.class), any(), anyCollection());
|
||||
verify(AccessDecisionManagerRefConfig.ACCESS_DECISION_MANAGER, times(1)).decide(any(Authentication.class),
|
||||
any(), anyCollection());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AccessDecisionManagerRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AccessDecisionManager ACCESS_DECISION_MANAGER;
|
||||
|
||||
@Override
|
||||
@@ -101,19 +106,20 @@ public class NamespaceHttpTests {
|
||||
.accessDecisionManager(ACCESS_DECISION_MANAGER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@access-denied-page
|
||||
@Test // http@access-denied-page
|
||||
public void configureWhenAccessDeniedPageSetAndRequestForbiddenThenForwardedToAccessDeniedPage() throws Exception {
|
||||
this.spring.register(AccessDeniedPageConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/admin").with(user(PasswordEncodedUser.user())))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(forwardedUrl("/AccessDeniedPage"));
|
||||
this.mockMvc.perform(get("/admin").with(user(PasswordEncodedUser.user()))).andExpect(status().isForbidden())
|
||||
.andExpect(forwardedUrl("/AccessDeniedPage"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AccessDeniedPageConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -126,9 +132,10 @@ public class NamespaceHttpTests {
|
||||
.accessDeniedPage("/AccessDeniedPage");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@authentication-manager-ref
|
||||
@Test // http@authentication-manager-ref
|
||||
public void configureWhenAuthenticationManagerProvidedThenVerifyUse() throws Exception {
|
||||
AuthenticationManagerRefConfig.AUTHENTICATION_MANAGER = mock(AuthenticationManager.class);
|
||||
this.spring.register(AuthenticationManagerRefConfig.class).autowire();
|
||||
@@ -140,6 +147,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthenticationManagerRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationManager AUTHENTICATION_MANAGER;
|
||||
|
||||
@Override
|
||||
@@ -157,9 +165,10 @@ public class NamespaceHttpTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@create-session=always
|
||||
@Test // http@create-session=always
|
||||
public void configureWhenSessionCreationPolicyAlwaysThenSessionCreatedOnRequest() throws Exception {
|
||||
this.spring.register(CreateSessionAlwaysConfig.class).autowire();
|
||||
|
||||
@@ -172,6 +181,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CreateSessionAlwaysConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -183,9 +193,10 @@ public class NamespaceHttpTests {
|
||||
.sessionCreationPolicy(SessionCreationPolicy.ALWAYS);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@create-session=stateless
|
||||
@Test // http@create-session=stateless
|
||||
public void configureWhenSessionCreationPolicyStatelessThenSessionNotCreatedOnRequest() throws Exception {
|
||||
this.spring.register(CreateSessionStatelessConfig.class).autowire();
|
||||
|
||||
@@ -197,6 +208,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CreateSessionStatelessConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -208,9 +220,10 @@ public class NamespaceHttpTests {
|
||||
.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@create-session=ifRequired
|
||||
@Test // http@create-session=ifRequired
|
||||
public void configureWhenSessionCreationPolicyIfRequiredThenSessionCreatedWhenRequiredOnRequest() throws Exception {
|
||||
this.spring.register(IfRequiredConfig.class).autowire();
|
||||
|
||||
@@ -228,6 +241,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IfRequiredConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -242,9 +256,10 @@ public class NamespaceHttpTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@create-session=never
|
||||
@Test // http@create-session=never
|
||||
public void configureWhenSessionCreationPolicyNeverThenSessionNotCreatedOnRequest() throws Exception {
|
||||
this.spring.register(CreateSessionNeverConfig.class).autowire();
|
||||
|
||||
@@ -256,6 +271,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CreateSessionNeverConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -267,19 +283,21 @@ public class NamespaceHttpTests {
|
||||
.sessionCreationPolicy(SessionCreationPolicy.NEVER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@entry-point-ref
|
||||
public void configureWhenAuthenticationEntryPointSetAndRequestUnauthorizedThenRedirectedToAuthenticationEntryPoint() throws Exception {
|
||||
@Test // http@entry-point-ref
|
||||
public void configureWhenAuthenticationEntryPointSetAndRequestUnauthorizedThenRedirectedToAuthenticationEntryPoint()
|
||||
throws Exception {
|
||||
this.spring.register(EntryPointRefConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(status().is3xxRedirection())
|
||||
.andExpect(redirectedUrlPattern("**/entry-point"));
|
||||
this.mockMvc.perform(get("/")).andExpect(status().is3xxRedirection())
|
||||
.andExpect(redirectedUrlPattern("**/entry-point"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EntryPointRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -293,9 +311,10 @@ public class NamespaceHttpTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@jaas-api-provision
|
||||
@Test // http@jaas-api-provision
|
||||
public void configureWhenJaasApiIntegrationFilterAddedThenJaasSubjectObtained() throws Exception {
|
||||
LoginContext loginContext = mock(LoginContext.class);
|
||||
when(loginContext.getSubject()).thenReturn(new Subject());
|
||||
@@ -313,6 +332,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class JaasApiProvisionConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
// @formatter:off
|
||||
@@ -320,19 +340,20 @@ public class NamespaceHttpTests {
|
||||
.addFilter(new JaasApiIntegrationFilter());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@realm
|
||||
@Test // http@realm
|
||||
public void configureWhenHttpBasicAndRequestUnauthorizedThenReturnWWWAuthenticateWithRealm() throws Exception {
|
||||
this.spring.register(RealmConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string("WWW-Authenticate", "Basic realm=\"RealmConfig\""));
|
||||
this.mockMvc.perform(get("/")).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string("WWW-Authenticate", "Basic realm=\"RealmConfig\""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RealmConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -344,21 +365,24 @@ public class NamespaceHttpTests {
|
||||
.realmName("RealmConfig");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@request-matcher-ref ant
|
||||
@Test // http@request-matcher-ref ant
|
||||
public void configureWhenAntPatternMatchingThenAntPathRequestMatcherUsed() {
|
||||
this.spring.register(RequestMatcherAntConfig.class).autowire();
|
||||
|
||||
FilterChainProxy filterChainProxy = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
|
||||
assertThat(filterChainProxy.getFilterChains().get(0)).isInstanceOf(DefaultSecurityFilterChain.class);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains().get(0);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains()
|
||||
.get(0);
|
||||
assertThat(securityFilterChain.getRequestMatcher()).isInstanceOf(AntPathRequestMatcher.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherAntConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
// @formatter:off
|
||||
@@ -366,21 +390,24 @@ public class NamespaceHttpTests {
|
||||
.antMatcher("/api/**");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@request-matcher-ref regex
|
||||
@Test // http@request-matcher-ref regex
|
||||
public void configureWhenRegexPatternMatchingThenRegexRequestMatcherUsed() {
|
||||
this.spring.register(RequestMatcherRegexConfig.class).autowire();
|
||||
|
||||
FilterChainProxy filterChainProxy = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
|
||||
assertThat(filterChainProxy.getFilterChains().get(0)).isInstanceOf(DefaultSecurityFilterChain.class);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains().get(0);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains()
|
||||
.get(0);
|
||||
assertThat(securityFilterChain.getRequestMatcher()).isInstanceOf(RegexRequestMatcher.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherRegexConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
// @formatter:off
|
||||
@@ -388,21 +415,25 @@ public class NamespaceHttpTests {
|
||||
.regexMatcher("/regex/.*");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@request-matcher-ref
|
||||
@Test // http@request-matcher-ref
|
||||
public void configureWhenRequestMatcherProvidedThenRequestMatcherUsed() {
|
||||
this.spring.register(RequestMatcherRefConfig.class).autowire();
|
||||
|
||||
FilterChainProxy filterChainProxy = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
|
||||
assertThat(filterChainProxy.getFilterChains().get(0)).isInstanceOf(DefaultSecurityFilterChain.class);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains().get(0);
|
||||
assertThat(securityFilterChain.getRequestMatcher()).isInstanceOf(RequestMatcherRefConfig.MyRequestMatcher.class);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains()
|
||||
.get(0);
|
||||
assertThat(securityFilterChain.getRequestMatcher())
|
||||
.isInstanceOf(RequestMatcherRefConfig.MyRequestMatcher.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherRefConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
// @formatter:off
|
||||
@@ -412,28 +443,34 @@ public class NamespaceHttpTests {
|
||||
}
|
||||
|
||||
static class MyRequestMatcher implements RequestMatcher {
|
||||
|
||||
public boolean matches(HttpServletRequest request) {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@security=none
|
||||
@Test // http@security=none
|
||||
public void configureWhenIgnoredAntPatternsThenAntPathRequestMatcherUsedWithNoFilters() {
|
||||
this.spring.register(SecurityNoneConfig.class).autowire();
|
||||
|
||||
FilterChainProxy filterChainProxy = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
|
||||
assertThat(filterChainProxy.getFilterChains().get(0)).isInstanceOf(DefaultSecurityFilterChain.class);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains().get(0);
|
||||
DefaultSecurityFilterChain securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains()
|
||||
.get(0);
|
||||
assertThat(securityFilterChain.getRequestMatcher()).isInstanceOf(AntPathRequestMatcher.class);
|
||||
assertThat(((AntPathRequestMatcher) securityFilterChain.getRequestMatcher()).getPattern()).isEqualTo("/resources/**");
|
||||
assertThat(((AntPathRequestMatcher) securityFilterChain.getRequestMatcher()).getPattern())
|
||||
.isEqualTo("/resources/**");
|
||||
assertThat(securityFilterChain.getFilters()).isEmpty();
|
||||
|
||||
assertThat(filterChainProxy.getFilterChains().get(1)).isInstanceOf(DefaultSecurityFilterChain.class);
|
||||
securityFilterChain = (DefaultSecurityFilterChain) filterChainProxy.getFilterChains().get(1);
|
||||
assertThat(securityFilterChain.getRequestMatcher()).isInstanceOf(AntPathRequestMatcher.class);
|
||||
assertThat(((AntPathRequestMatcher) securityFilterChain.getRequestMatcher()).getPattern()).isEqualTo("/public/**");
|
||||
assertThat(((AntPathRequestMatcher) securityFilterChain.getRequestMatcher()).getPattern())
|
||||
.isEqualTo("/public/**");
|
||||
assertThat(securityFilterChain.getFilters()).isEmpty();
|
||||
}
|
||||
|
||||
@@ -442,17 +479,16 @@ public class NamespaceHttpTests {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web
|
||||
.ignoring()
|
||||
.antMatchers("/resources/**", "/public/**");
|
||||
web.ignoring().antMatchers("/resources/**", "/public/**");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@security-context-repository-ref
|
||||
@Test // http@security-context-repository-ref
|
||||
public void configureWhenNullSecurityContextRepositoryThenSecurityContextNotSavedInSession() throws Exception {
|
||||
this.spring.register(SecurityContextRepoConfig.class).autowire();
|
||||
|
||||
@@ -463,6 +499,7 @@ public class NamespaceHttpTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class SecurityContextRepoConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -485,19 +522,22 @@ public class NamespaceHttpTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@servlet-api-provision=false
|
||||
@Test // http@servlet-api-provision=false
|
||||
public void configureWhenServletApiDisabledThenRequestNotServletApiWrapper() throws Exception {
|
||||
this.spring.register(ServletApiProvisionConfig.class, MainController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"));
|
||||
|
||||
assertThat(MainController.HTTP_SERVLET_REQUEST_TYPE).isNotInstanceOf(SecurityContextHolderAwareRequestWrapper.class);
|
||||
assertThat(MainController.HTTP_SERVLET_REQUEST_TYPE)
|
||||
.isNotInstanceOf(SecurityContextHolderAwareRequestWrapper.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ServletApiProvisionConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -509,19 +549,22 @@ public class NamespaceHttpTests {
|
||||
.disable();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@servlet-api-provision defaults to true
|
||||
@Test // http@servlet-api-provision defaults to true
|
||||
public void configureWhenServletApiDefaultThenRequestIsServletApiWrapper() throws Exception {
|
||||
this.spring.register(ServletApiProvisionDefaultsConfig.class, MainController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"));
|
||||
|
||||
assertThat(SecurityContextHolderAwareRequestWrapper.class).isAssignableFrom(MainController.HTTP_SERVLET_REQUEST_TYPE);
|
||||
assertThat(SecurityContextHolderAwareRequestWrapper.class)
|
||||
.isAssignableFrom(MainController.HTTP_SERVLET_REQUEST_TYPE);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ServletApiProvisionDefaultsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -530,10 +573,12 @@ public class NamespaceHttpTests {
|
||||
.anyRequest().permitAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Controller
|
||||
static class MainController {
|
||||
|
||||
static Class<? extends HttpServletRequest> HTTP_SERVLET_REQUEST_TYPE;
|
||||
|
||||
@GetMapping("/")
|
||||
@@ -541,20 +586,22 @@ public class NamespaceHttpTests {
|
||||
HTTP_SERVLET_REQUEST_TYPE = request.getClass();
|
||||
return "index";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@use-expressions=true
|
||||
@Test // http@use-expressions=true
|
||||
public void configureWhenUseExpressionsEnabledThenExpressionBasedSecurityMetadataSource() {
|
||||
this.spring.register(UseExpressionsConfig.class).autowire();
|
||||
|
||||
UseExpressionsConfig config = this.spring.getContext().getBean(UseExpressionsConfig.class);
|
||||
|
||||
assertThat(ExpressionBasedFilterInvocationSecurityMetadataSource.class)
|
||||
.isAssignableFrom(config.filterInvocationSecurityMetadataSourceType);
|
||||
.isAssignableFrom(config.filterInvocationSecurityMetadataSourceType);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class UseExpressionsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
private Class<? extends FilterInvocationSecurityMetadataSource> filterInvocationSecurityMetadataSourceType;
|
||||
|
||||
@Override
|
||||
@@ -574,24 +621,26 @@ public class NamespaceHttpTests {
|
||||
final HttpSecurity http = this.getHttp();
|
||||
web.postBuildAction(() -> {
|
||||
FilterSecurityInterceptor securityInterceptor = http.getSharedObject(FilterSecurityInterceptor.class);
|
||||
UseExpressionsConfig.this.filterInvocationSecurityMetadataSourceType =
|
||||
securityInterceptor.getSecurityMetadataSource().getClass();
|
||||
UseExpressionsConfig.this.filterInvocationSecurityMetadataSourceType = securityInterceptor
|
||||
.getSecurityMetadataSource().getClass();
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test // http@use-expressions=false
|
||||
@Test // http@use-expressions=false
|
||||
public void configureWhenUseExpressionsDisabledThenDefaultSecurityMetadataSource() {
|
||||
this.spring.register(DisableUseExpressionsConfig.class).autowire();
|
||||
|
||||
DisableUseExpressionsConfig config = this.spring.getContext().getBean(DisableUseExpressionsConfig.class);
|
||||
|
||||
assertThat(DefaultFilterInvocationSecurityMetadataSource.class)
|
||||
.isAssignableFrom(config.filterInvocationSecurityMetadataSourceType);
|
||||
.isAssignableFrom(config.filterInvocationSecurityMetadataSourceType);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DisableUseExpressionsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
private Class<? extends FilterInvocationSecurityMetadataSource> filterInvocationSecurityMetadataSourceType;
|
||||
|
||||
@Override
|
||||
@@ -611,9 +660,11 @@ public class NamespaceHttpTests {
|
||||
final HttpSecurity http = this.getHttp();
|
||||
web.postBuildAction(() -> {
|
||||
FilterSecurityInterceptor securityInterceptor = http.getSharedObject(FilterSecurityInterceptor.class);
|
||||
DisableUseExpressionsConfig.this.filterInvocationSecurityMetadataSourceType =
|
||||
securityInterceptor.getSecurityMetadataSource().getClass();
|
||||
DisableUseExpressionsConfig.this.filterInvocationSecurityMetadataSourceType = securityInterceptor
|
||||
.getSecurityMetadataSource().getClass();
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -45,10 +45,13 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class WebSecurityTests {
|
||||
|
||||
AnnotationConfigWebApplicationContext context;
|
||||
|
||||
MockHttpServletRequest request;
|
||||
|
||||
MockHttpServletResponse response;
|
||||
|
||||
MockFilterChain chain;
|
||||
|
||||
@Autowired
|
||||
@@ -97,14 +100,14 @@ public class WebSecurityTests {
|
||||
this.request.setRequestURI("/other");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
// @formatter:off
|
||||
@@ -134,11 +137,14 @@ public class WebSecurityTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -173,14 +179,14 @@ public class WebSecurityTests {
|
||||
this.request.setRequestURI("/other/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherServletPathConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
// @formatter:off
|
||||
@@ -211,19 +217,24 @@ public class WebSecurityTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class LegacyMvcMatchingConfig implements WebMvcConfigurer {
|
||||
|
||||
@Override
|
||||
public void configurePathMatch(PathMatchConfigurer configurer) {
|
||||
configurer.setUseSuffixPatternMatch(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void loadConfig(Class<?>... configs) {
|
||||
|
||||
@@ -42,7 +42,6 @@ import org.springframework.web.context.WebApplicationContext;
|
||||
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Rob Winch
|
||||
*
|
||||
*/
|
||||
@@ -50,6 +49,7 @@ import org.springframework.web.servlet.config.annotation.EnableWebMvc;
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class AuthenticationPrincipalArgumentResolverTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext wac;
|
||||
|
||||
@@ -62,21 +62,19 @@ public class AuthenticationPrincipalArgumentResolverTests {
|
||||
public void authenticationPrincipalExpressionWhenBeanExpressionSuppliedThenBeanUsed() throws Exception {
|
||||
User user = new User("user", "password", AuthorityUtils.createAuthorityList("ROLE_USER"));
|
||||
SecurityContext context = SecurityContextHolder.createEmptyContext();
|
||||
context.setAuthentication(new UsernamePasswordAuthenticationToken(user, user.getPassword(), user.getAuthorities()));
|
||||
context.setAuthentication(
|
||||
new UsernamePasswordAuthenticationToken(user, user.getPassword(), user.getAuthorities()));
|
||||
SecurityContextHolder.setContext(context);
|
||||
|
||||
MockMvc mockMvc = MockMvcBuilders
|
||||
.webAppContextSetup(wac)
|
||||
.build();
|
||||
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();
|
||||
|
||||
mockMvc.perform(get("/users/self"))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(content().string("extracted-user"));
|
||||
mockMvc.perform(get("/users/self")).andExpect(status().isOk()).andExpect(content().string("extracted-user"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class Config {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
|
||||
@@ -45,6 +45,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class EnableWebSecurityTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -56,12 +57,14 @@ public class EnableWebSecurityTests {
|
||||
this.spring.register(SecurityConfig.class).autowire();
|
||||
|
||||
AuthenticationManager authenticationManager = this.spring.getContext().getBean(AuthenticationManager.class);
|
||||
Authentication authentication = authenticationManager.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
Authentication authentication = authenticationManager
|
||||
.authenticate(new UsernamePasswordAuthenticationToken("user", "password"));
|
||||
assertThat(authentication.isAuthenticated()).isTrue();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class SecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -87,6 +90,7 @@ public class EnableWebSecurityTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -97,10 +101,12 @@ public class EnableWebSecurityTests {
|
||||
|
||||
@Configuration
|
||||
static class ChildSecurityConfig extends DebugSecurityConfig {
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity(debug=true)
|
||||
@EnableWebSecurity(debug = true)
|
||||
static class DebugSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -108,12 +114,13 @@ public class EnableWebSecurityTests {
|
||||
this.spring.register(AuthenticationPrincipalConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/").with(authentication(new TestingAuthenticationToken("user1", "password"))))
|
||||
.andExpect(content().string("user1"));
|
||||
.andExpect(content().string("user1"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class AuthenticationPrincipalConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
@@ -125,7 +132,9 @@ public class EnableWebSecurityTests {
|
||||
String principal(@AuthenticationPrincipal String principal) {
|
||||
return principal;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -133,12 +142,13 @@ public class EnableWebSecurityTests {
|
||||
this.spring.register(SecurityFilterChainAuthenticationPrincipalConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/").with(authentication(new TestingAuthenticationToken("user1", "password"))))
|
||||
.andExpect(content().string("user1"));
|
||||
.andExpect(content().string("user1"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class SecurityFilterChainAuthenticationPrincipalConfig {
|
||||
|
||||
@Bean
|
||||
SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http.build();
|
||||
@@ -151,7 +161,9 @@ public class EnableWebSecurityTests {
|
||||
String principal(@AuthenticationPrincipal String principal) {
|
||||
return principal;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -166,6 +178,7 @@ public class EnableWebSecurityTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class BeanProxyEnabledByDefaultConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Bean
|
||||
public Child child() {
|
||||
return new Child();
|
||||
@@ -175,6 +188,7 @@ public class EnableWebSecurityTests {
|
||||
public Parent parent() {
|
||||
return new Parent(child());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -190,6 +204,7 @@ public class EnableWebSecurityTests {
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableWebSecurity
|
||||
static class BeanProxyDisabledConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Bean
|
||||
public Child child() {
|
||||
return new Child();
|
||||
@@ -199,9 +214,11 @@ public class EnableWebSecurityTests {
|
||||
public Parent parent() {
|
||||
return new Parent(child());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class Parent {
|
||||
|
||||
private Child child;
|
||||
|
||||
Parent(Child child) {
|
||||
@@ -211,10 +228,14 @@ public class EnableWebSecurityTests {
|
||||
public Child getChild() {
|
||||
return child;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class Child {
|
||||
|
||||
Child() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -62,6 +62,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Eleftheria Stein
|
||||
*/
|
||||
public class HttpSecurityConfigurationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -70,11 +71,9 @@ public class HttpSecurityConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void postWhenDefaultFilterChainBeanThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(DefaultWithFilterChainConfig.class)
|
||||
.autowire();
|
||||
this.spring.register(DefaultWithFilterChainConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(post("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mockMvc.perform(post("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -83,13 +82,14 @@ public class HttpSecurityConfigurationTests {
|
||||
|
||||
MvcResult mvcResult = this.mockMvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff"))
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS, XFrameOptionsHeaderWriter.XFrameOptionsMode.DENY.name()))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS,
|
||||
XFrameOptionsHeaderWriter.XFrameOptionsMode.DENY.name()))
|
||||
.andExpect(
|
||||
header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactlyInAnyOrder(
|
||||
HttpHeaders.X_CONTENT_TYPE_OPTIONS, HttpHeaders.X_FRAME_OPTIONS, HttpHeaders.STRICT_TRANSPORT_SECURITY,
|
||||
HttpHeaders.CACHE_CONTROL, HttpHeaders.EXPIRES, HttpHeaders.PRAGMA, HttpHeaders.X_XSS_PROTECTION);
|
||||
@@ -99,57 +99,54 @@ public class HttpSecurityConfigurationTests {
|
||||
public void logoutWhenDefaultFilterChainBeanThenCreatesDefaultLogoutEndpoint() throws Exception {
|
||||
this.spring.register(DefaultWithFilterChainConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(post("/logout").with(csrf()))
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mockMvc.perform(post("/logout").with(csrf())).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenDefaultConfigThenWebAsyncManagerIntegrationFilterAdded() throws Exception {
|
||||
this.spring.register(DefaultWithFilterChainConfig.class, NameController.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mockMvc.perform(get("/name").with(user("Bob")))
|
||||
.andExpect(request().asyncStarted())
|
||||
MvcResult mvcResult = this.mockMvc.perform(get("/name").with(user("Bob"))).andExpect(request().asyncStarted())
|
||||
.andReturn();
|
||||
|
||||
this.mockMvc.perform(asyncDispatch(mvcResult))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(content().string("Bob"));
|
||||
this.mockMvc.perform(asyncDispatch(mvcResult)).andExpect(status().isOk()).andExpect(content().string("Bob"));
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class NameController {
|
||||
|
||||
@GetMapping("/name")
|
||||
public Callable<String> name() {
|
||||
return () -> SecurityContextHolder.getContext().getAuthentication().getName();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultWithFilterChainConfig {
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenDefaultFilterChainBeanThenAnonymousPermitted() throws Exception {
|
||||
this.spring.register(AuthorizeRequestsConfig.class, UserDetailsConfig.class, BaseController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mockMvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthorizeRequestsConfig {
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().permitAll()
|
||||
)
|
||||
.build();
|
||||
return http.authorizeRequests(authorize -> authorize.anyRequest().permitAll()).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -159,13 +156,9 @@ public class HttpSecurityConfigurationTests {
|
||||
MockHttpSession session = new MockHttpSession();
|
||||
String sessionId = session.getId();
|
||||
|
||||
MvcResult result =
|
||||
this.mockMvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password")
|
||||
.session(session)
|
||||
.with(csrf()))
|
||||
.andReturn();
|
||||
MvcResult result = this.mockMvc.perform(
|
||||
post("/login").param("username", "user").param("password", "password").session(session).with(csrf()))
|
||||
.andReturn();
|
||||
|
||||
assertThat(result.getRequest().getSession(false).getId()).isNotEqualTo(sessionId);
|
||||
}
|
||||
@@ -174,15 +167,11 @@ public class HttpSecurityConfigurationTests {
|
||||
public void authenticateWhenDefaultFilterChainBeanThenRedirectsToSavedRequest() throws Exception {
|
||||
this.spring.register(SecurityEnabledConfig.class, UserDetailsConfig.class).autowire();
|
||||
|
||||
MockHttpSession session = (MockHttpSession)
|
||||
this.mockMvc.perform(get("/messages"))
|
||||
.andReturn().getRequest().getSession();
|
||||
MockHttpSession session = (MockHttpSession) this.mockMvc.perform(get("/messages")).andReturn().getRequest()
|
||||
.getSession();
|
||||
|
||||
this.mockMvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password")
|
||||
.session(session)
|
||||
.with(csrf()))
|
||||
this.mockMvc.perform(
|
||||
post("/login").param("username", "user").param("password", "password").session(session).with(csrf()))
|
||||
.andExpect(redirectedUrl("http://localhost/messages"));
|
||||
}
|
||||
|
||||
@@ -190,8 +179,9 @@ public class HttpSecurityConfigurationTests {
|
||||
public void authenticateWhenDefaultFilterChainBeanThenRolePrefixIsSet() throws Exception {
|
||||
this.spring.register(SecurityEnabledConfig.class, UserDetailsConfig.class, UserController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/user")
|
||||
.with(authentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"))))
|
||||
this.mockMvc
|
||||
.perform(get("/user")
|
||||
.with(authentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@@ -199,50 +189,51 @@ public class HttpSecurityConfigurationTests {
|
||||
public void loginWhenUsingDefaultsThenDefaultLoginPageGenerated() throws Exception {
|
||||
this.spring.register(SecurityEnabledConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login"))
|
||||
.andExpect(status().isOk());
|
||||
this.mockMvc.perform(get("/login")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class SecurityEnabledConfig {
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().authenticated()
|
||||
)
|
||||
.formLogin(withDefaults())
|
||||
return http.authorizeRequests(authorize -> authorize.anyRequest().authenticated()).formLogin(withDefaults())
|
||||
.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class UserDetailsConfig {
|
||||
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
UserDetails user = User.withDefaultPasswordEncoder()
|
||||
.username("user")
|
||||
.password("password")
|
||||
.roles("USER")
|
||||
UserDetails user = User.withDefaultPasswordEncoder().username("user").password("password").roles("USER")
|
||||
.build();
|
||||
return new InMemoryUserDetailsManager(user);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class BaseController {
|
||||
|
||||
@GetMapping("/")
|
||||
public void index() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class UserController {
|
||||
|
||||
@GetMapping("/user")
|
||||
public void user(HttpServletRequest request) {
|
||||
if (!request.isUserInRole("USER")) {
|
||||
throw new AccessDeniedException("This resource is only available to users");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -64,6 +64,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class OAuth2ClientConfigurationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -78,14 +79,14 @@ public class OAuth2ClientConfigurationTests {
|
||||
|
||||
ClientRegistrationRepository clientRegistrationRepository = mock(ClientRegistrationRepository.class);
|
||||
ClientRegistration clientRegistration = clientRegistration().registrationId(clientRegistrationId).build();
|
||||
when(clientRegistrationRepository.findByRegistrationId(eq(clientRegistrationId))).thenReturn(clientRegistration);
|
||||
when(clientRegistrationRepository.findByRegistrationId(eq(clientRegistrationId)))
|
||||
.thenReturn(clientRegistration);
|
||||
|
||||
OAuth2AuthorizedClientRepository authorizedClientRepository = mock(OAuth2AuthorizedClientRepository.class);
|
||||
OAuth2AuthorizedClient authorizedClient = mock(OAuth2AuthorizedClient.class);
|
||||
when(authorizedClient.getClientRegistration()).thenReturn(clientRegistration);
|
||||
when(authorizedClientRepository.loadAuthorizedClient(
|
||||
eq(clientRegistrationId), eq(authentication), any(HttpServletRequest.class)))
|
||||
.thenReturn(authorizedClient);
|
||||
when(authorizedClientRepository.loadAuthorizedClient(eq(clientRegistrationId), eq(authentication),
|
||||
any(HttpServletRequest.class))).thenReturn(authorizedClient);
|
||||
|
||||
OAuth2AccessToken accessToken = mock(OAuth2AccessToken.class);
|
||||
when(authorizedClient.getAccessToken()).thenReturn(accessToken);
|
||||
@@ -97,14 +98,14 @@ public class OAuth2ClientConfigurationTests {
|
||||
OAuth2AuthorizedClientArgumentResolverConfig.ACCESS_TOKEN_RESPONSE_CLIENT = accessTokenResponseClient;
|
||||
this.spring.register(OAuth2AuthorizedClientArgumentResolverConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication)))
|
||||
.andExpect(status().isOk())
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication))).andExpect(status().isOk())
|
||||
.andExpect(content().string("resolved"));
|
||||
verifyZeroInteractions(accessTokenResponseClient);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenAuthorizedClientNotFoundAndClientCredentialsThenTokenResponseClientIsUsed() throws Exception {
|
||||
public void requestWhenAuthorizedClientNotFoundAndClientCredentialsThenTokenResponseClientIsUsed()
|
||||
throws Exception {
|
||||
String clientRegistrationId = "client1";
|
||||
String principalName = "user1";
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken(principalName, "password");
|
||||
@@ -117,9 +118,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
when(clientRegistrationRepository.findByRegistrationId(clientRegistrationId)).thenReturn(clientRegistration);
|
||||
|
||||
OAuth2AccessTokenResponse accessTokenResponse = OAuth2AccessTokenResponse.withToken("access-token-1234")
|
||||
.tokenType(OAuth2AccessToken.TokenType.BEARER)
|
||||
.expiresIn(300)
|
||||
.build();
|
||||
.tokenType(OAuth2AccessToken.TokenType.BEARER).expiresIn(300).build();
|
||||
when(accessTokenResponseClient.getTokenResponse(any(OAuth2ClientCredentialsGrantRequest.class)))
|
||||
.thenReturn(accessTokenResponse);
|
||||
|
||||
@@ -128,8 +127,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
OAuth2AuthorizedClientArgumentResolverConfig.ACCESS_TOKEN_RESPONSE_CLIENT = accessTokenResponseClient;
|
||||
this.spring.register(OAuth2AuthorizedClientArgumentResolverConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication)))
|
||||
.andExpect(status().isOk())
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication))).andExpect(status().isOk())
|
||||
.andExpect(content().string("resolved"));
|
||||
verify(accessTokenResponseClient, times(1)).getTokenResponse(any(OAuth2ClientCredentialsGrantRequest.class));
|
||||
}
|
||||
@@ -137,6 +135,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
@EnableWebMvc
|
||||
@EnableWebSecurity
|
||||
static class OAuth2AuthorizedClientArgumentResolverConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ClientRegistrationRepository CLIENT_REGISTRATION_REPOSITORY;
|
||||
static OAuth2AuthorizedClientRepository AUTHORIZED_CLIENT_REPOSITORY;
|
||||
static OAuth2AccessTokenResponseClient<OAuth2ClientCredentialsGrantRequest> ACCESS_TOKEN_RESPONSE_CLIENT;
|
||||
@@ -149,9 +148,11 @@ public class OAuth2ClientConfigurationTests {
|
||||
public class Controller {
|
||||
|
||||
@GetMapping("/authorized-client")
|
||||
public String authorizedClient(@RegisteredOAuth2AuthorizedClient("client1") OAuth2AuthorizedClient authorizedClient) {
|
||||
public String authorizedClient(
|
||||
@RegisteredOAuth2AuthorizedClient("client1") OAuth2AuthorizedClient authorizedClient) {
|
||||
return authorizedClient != null ? "resolved" : "not-resolved";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Bean
|
||||
@@ -168,15 +169,18 @@ public class OAuth2ClientConfigurationTests {
|
||||
public OAuth2AccessTokenResponseClient<OAuth2ClientCredentialsGrantRequest> accessTokenResponseClient() {
|
||||
return ACCESS_TOKEN_RESPONSE_CLIENT;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-5321
|
||||
@Test
|
||||
public void loadContextWhenOAuth2AuthorizedClientRepositoryRegisteredTwiceThenThrowNoUniqueBeanDefinitionException() {
|
||||
assertThatThrownBy(() -> this.spring.register(OAuth2AuthorizedClientRepositoryRegisteredTwiceConfig.class).autowire())
|
||||
.hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class)
|
||||
.hasMessageContaining("Expected single matching bean of type '" + OAuth2AuthorizedClientRepository.class.getName() +
|
||||
"' but found 2: authorizedClientRepository1,authorizedClientRepository2");
|
||||
assertThatThrownBy(
|
||||
() -> this.spring.register(OAuth2AuthorizedClientRepositoryRegisteredTwiceConfig.class).autowire())
|
||||
.hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class)
|
||||
.hasMessageContaining("Expected single matching bean of type '"
|
||||
+ OAuth2AuthorizedClientRepository.class.getName()
|
||||
+ "' but found 2: authorizedClientRepository1,authorizedClientRepository2");
|
||||
}
|
||||
|
||||
@EnableWebMvc
|
||||
@@ -213,13 +217,14 @@ public class OAuth2ClientConfigurationTests {
|
||||
public OAuth2AccessTokenResponseClient<OAuth2ClientCredentialsGrantRequest> accessTokenResponseClient() {
|
||||
return mock(OAuth2AccessTokenResponseClient.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadContextWhenClientRegistrationRepositoryNotRegisteredThenThrowNoSuchBeanDefinitionException() {
|
||||
assertThatThrownBy(() -> this.spring.register(ClientRegistrationRepositoryNotRegisteredConfig.class).autowire())
|
||||
.hasRootCauseInstanceOf(NoSuchBeanDefinitionException.class)
|
||||
.hasMessageContaining("No qualifying bean of type '" + ClientRegistrationRepository.class.getName() + "' available");
|
||||
.hasRootCauseInstanceOf(NoSuchBeanDefinitionException.class).hasMessageContaining(
|
||||
"No qualifying bean of type '" + ClientRegistrationRepository.class.getName() + "' available");
|
||||
}
|
||||
|
||||
@EnableWebMvc
|
||||
@@ -236,13 +241,14 @@ public class OAuth2ClientConfigurationTests {
|
||||
.oauth2Login();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadContextWhenClientRegistrationRepositoryRegisteredTwiceThenThrowNoUniqueBeanDefinitionException() {
|
||||
assertThatThrownBy(() -> this.spring.register(ClientRegistrationRepositoryRegisteredTwiceConfig.class).autowire())
|
||||
.hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class)
|
||||
.hasMessageContaining("expected single matching bean but found 2: clientRegistrationRepository1,clientRegistrationRepository2");
|
||||
assertThatThrownBy(() -> this.spring.register(ClientRegistrationRepositoryRegisteredTwiceConfig.class)
|
||||
.autowire()).hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class).hasMessageContaining(
|
||||
"expected single matching bean but found 2: clientRegistrationRepository1,clientRegistrationRepository2");
|
||||
}
|
||||
|
||||
@EnableWebMvc
|
||||
@@ -279,13 +285,14 @@ public class OAuth2ClientConfigurationTests {
|
||||
public OAuth2AccessTokenResponseClient<OAuth2ClientCredentialsGrantRequest> accessTokenResponseClient() {
|
||||
return mock(OAuth2AccessTokenResponseClient.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadContextWhenAccessTokenResponseClientRegisteredTwiceThenThrowNoUniqueBeanDefinitionException() {
|
||||
assertThatThrownBy(() -> this.spring.register(AccessTokenResponseClientRegisteredTwiceConfig.class).autowire())
|
||||
.hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class)
|
||||
.hasMessageContaining("expected single matching bean but found 2: accessTokenResponseClient1,accessTokenResponseClient2");
|
||||
.hasRootCauseInstanceOf(NoUniqueBeanDefinitionException.class).hasMessageContaining(
|
||||
"expected single matching bean but found 2: accessTokenResponseClient1,accessTokenResponseClient2");
|
||||
}
|
||||
|
||||
@EnableWebMvc
|
||||
@@ -322,6 +329,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
public OAuth2AccessTokenResponseClient<OAuth2ClientCredentialsGrantRequest> accessTokenResponseClient2() {
|
||||
return mock(OAuth2AccessTokenResponseClient.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-8700
|
||||
@@ -336,8 +344,8 @@ public class OAuth2ClientConfigurationTests {
|
||||
OAuth2AuthorizedClientManager authorizedClientManager = mock(OAuth2AuthorizedClientManager.class);
|
||||
|
||||
ClientRegistration clientRegistration = clientRegistration().registrationId(clientRegistrationId).build();
|
||||
OAuth2AuthorizedClient authorizedClient = new OAuth2AuthorizedClient(
|
||||
clientRegistration, principalName, TestOAuth2AccessTokens.noScopes());
|
||||
OAuth2AuthorizedClient authorizedClient = new OAuth2AuthorizedClient(clientRegistration, principalName,
|
||||
TestOAuth2AccessTokens.noScopes());
|
||||
|
||||
when(authorizedClientManager.authorize(any())).thenReturn(authorizedClient);
|
||||
|
||||
@@ -346,8 +354,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
OAuth2AuthorizedClientManagerRegisteredConfig.AUTHORIZED_CLIENT_MANAGER = authorizedClientManager;
|
||||
this.spring.register(OAuth2AuthorizedClientManagerRegisteredConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication)))
|
||||
.andExpect(status().isOk())
|
||||
this.mockMvc.perform(get("/authorized-client").with(authentication(authentication))).andExpect(status().isOk())
|
||||
.andExpect(content().string("resolved"));
|
||||
|
||||
verify(authorizedClientManager).authorize(any());
|
||||
@@ -358,6 +365,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
@EnableWebMvc
|
||||
@EnableWebSecurity
|
||||
static class OAuth2AuthorizedClientManagerRegisteredConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ClientRegistrationRepository CLIENT_REGISTRATION_REPOSITORY;
|
||||
static OAuth2AuthorizedClientRepository AUTHORIZED_CLIENT_REPOSITORY;
|
||||
static OAuth2AuthorizedClientManager AUTHORIZED_CLIENT_MANAGER;
|
||||
@@ -370,9 +378,11 @@ public class OAuth2ClientConfigurationTests {
|
||||
public class Controller {
|
||||
|
||||
@GetMapping("/authorized-client")
|
||||
public String authorizedClient(@RegisteredOAuth2AuthorizedClient("client1") OAuth2AuthorizedClient authorizedClient) {
|
||||
public String authorizedClient(
|
||||
@RegisteredOAuth2AuthorizedClient("client1") OAuth2AuthorizedClient authorizedClient) {
|
||||
return authorizedClient != null ? "resolved" : "not-resolved";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Bean
|
||||
@@ -389,5 +399,7 @@ public class OAuth2ClientConfigurationTests {
|
||||
public OAuth2AuthorizedClientManager authorizedClientManager() {
|
||||
return AUTHORIZED_CLIENT_MANAGER;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -34,6 +34,7 @@ import static org.mockito.Mockito.mock;
|
||||
* @author Joe Grandja
|
||||
*/
|
||||
public class Sec2515Tests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -51,6 +52,7 @@ public class Sec2515Tests {
|
||||
public AuthenticationManager authenticationManagerBean() throws Exception {
|
||||
return super.authenticationManagerBean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test(expected = FatalBeanException.class)
|
||||
@@ -62,10 +64,11 @@ public class Sec2515Tests {
|
||||
static class CustomBeanNameStackOverflowSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
@Bean(name="custom")
|
||||
@Bean(name = "custom")
|
||||
public AuthenticationManager authenticationManagerBean() throws Exception {
|
||||
return super.authenticationManagerBean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2549
|
||||
@@ -73,7 +76,8 @@ public class Sec2515Tests {
|
||||
public void loadConfigWhenChildClassLoaderSetThenContextLoads() {
|
||||
CanLoadWithChildConfig.AUTHENTICATION_MANAGER = mock(AuthenticationManager.class);
|
||||
this.spring.register(CanLoadWithChildConfig.class);
|
||||
AnnotationConfigWebApplicationContext context = (AnnotationConfigWebApplicationContext) this.spring.getContext();
|
||||
AnnotationConfigWebApplicationContext context = (AnnotationConfigWebApplicationContext) this.spring
|
||||
.getContext();
|
||||
context.setClassLoader(new URLClassLoader(new URL[0], context.getClassLoader()));
|
||||
this.spring.autowire();
|
||||
|
||||
@@ -82,12 +86,14 @@ public class Sec2515Tests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CanLoadWithChildConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationManager AUTHENTICATION_MANAGER;
|
||||
|
||||
@Bean
|
||||
public AuthenticationManager authenticationManager() {
|
||||
return AUTHENTICATION_MANAGER;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2515
|
||||
@@ -109,5 +115,7 @@ public class Sec2515Tests {
|
||||
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -44,11 +44,13 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
|
||||
|
||||
/**
|
||||
* Tests for applications of {@link SecurityReactorContextConfiguration} in resource servers.
|
||||
* Tests for applications of {@link SecurityReactorContextConfiguration} in resource
|
||||
* servers.
|
||||
*
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -61,9 +63,7 @@ public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
BearerTokenAuthentication authentication = bearer();
|
||||
this.spring.register(BearerFilterConfig.class, WebServerConfig.class, Controller.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/token")
|
||||
.with(authentication(authentication)))
|
||||
.andExpect(status().isOk())
|
||||
this.mockMvc.perform(get("/token").with(authentication(authentication))).andExpect(status().isOk())
|
||||
.andExpect(content().string("Bearer token"));
|
||||
}
|
||||
|
||||
@@ -73,30 +73,28 @@ public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
BearerTokenAuthentication authentication = bearer();
|
||||
this.spring.register(BearerFilterlessConfig.class, WebServerConfig.class, Controller.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/token")
|
||||
.with(authentication(authentication)))
|
||||
.andExpect(status().isOk())
|
||||
this.mockMvc.perform(get("/token").with(authentication(authentication))).andExpect(status().isOk())
|
||||
.andExpect(content().string(""));
|
||||
}
|
||||
|
||||
|
||||
@EnableWebSecurity
|
||||
static class BearerFilterConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
}
|
||||
|
||||
@Bean
|
||||
WebClient rest() {
|
||||
ServletBearerExchangeFilterFunction bearer =
|
||||
new ServletBearerExchangeFilterFunction();
|
||||
return WebClient.builder()
|
||||
.filter(bearer).build();
|
||||
ServletBearerExchangeFilterFunction bearer = new ServletBearerExchangeFilterFunction();
|
||||
return WebClient.builder().filter(bearer).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class BearerFilterlessConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
}
|
||||
@@ -105,35 +103,33 @@ public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
WebClient rest() {
|
||||
return WebClient.create();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class Controller {
|
||||
|
||||
private final WebClient rest;
|
||||
|
||||
private final String uri;
|
||||
|
||||
@Autowired
|
||||
Controller(MockWebServer server, WebClient rest) {
|
||||
Controller(MockWebServer server, WebClient rest) {
|
||||
this.uri = server.url("/").toString();
|
||||
this.rest = rest;
|
||||
}
|
||||
|
||||
@GetMapping("/token")
|
||||
public String token() {
|
||||
return this.rest.get()
|
||||
.uri(this.uri)
|
||||
.retrieve()
|
||||
.bodyToMono(String.class)
|
||||
.flatMap(result -> this.rest.get()
|
||||
.uri(this.uri)
|
||||
.retrieve()
|
||||
.bodyToMono(String.class))
|
||||
.block();
|
||||
return this.rest.get().uri(this.uri).retrieve().bodyToMono(String.class)
|
||||
.flatMap(result -> this.rest.get().uri(this.uri).retrieve().bodyToMono(String.class)).block();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class WebServerConfig {
|
||||
|
||||
private final MockWebServer server = new MockWebServer();
|
||||
|
||||
@Bean
|
||||
@@ -147,6 +143,7 @@ public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
void shutdown() throws Exception {
|
||||
this.server.shutdown();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class AuthorizationHeaderDispatcher extends Dispatcher {
|
||||
@@ -161,5 +158,7 @@ public class SecurityReactorContextConfigurationResourceServerTests {
|
||||
}
|
||||
return response.setBody(header);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -59,11 +59,14 @@ import static org.springframework.security.config.annotation.web.configuration.S
|
||||
* @since 5.2
|
||||
*/
|
||||
public class SecurityReactorContextConfigurationTests {
|
||||
|
||||
private MockHttpServletRequest servletRequest;
|
||||
|
||||
private MockHttpServletResponse servletResponse;
|
||||
|
||||
private Authentication authentication;
|
||||
private SecurityReactorContextConfiguration.SecurityReactorContextSubscriberRegistrar subscriberRegistrar =
|
||||
new SecurityReactorContextConfiguration.SecurityReactorContextSubscriberRegistrar();
|
||||
|
||||
private SecurityReactorContextConfiguration.SecurityReactorContextSubscriberRegistrar subscriberRegistrar = new SecurityReactorContextConfiguration.SecurityReactorContextSubscriberRegistrar();
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
@@ -90,14 +93,15 @@ public class SecurityReactorContextConfigurationTests {
|
||||
return context;
|
||||
}
|
||||
};
|
||||
CoreSubscriber<Object> resultSubscriber = this.subscriberRegistrar.createSubscriberIfNecessary(originalSubscriber);
|
||||
CoreSubscriber<Object> resultSubscriber = this.subscriberRegistrar
|
||||
.createSubscriberIfNecessary(originalSubscriber);
|
||||
assertThat(resultSubscriber).isSameAs(originalSubscriber);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void createSubscriberIfNecessaryWhenWebSecurityContextAvailableThenCreateWithParentContext() {
|
||||
RequestContextHolder.setRequestAttributes(
|
||||
new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
RequestContextHolder
|
||||
.setRequestAttributes(new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
SecurityContextHolder.getContext().setAuthentication(this.authentication);
|
||||
|
||||
String testKey = "test_key";
|
||||
@@ -116,16 +120,15 @@ public class SecurityReactorContextConfigurationTests {
|
||||
assertThat(resultContext.getOrEmpty(testKey)).hasValue(testValue);
|
||||
Map<Object, Object> securityContextAttributes = resultContext.getOrDefault(SECURITY_CONTEXT_ATTRIBUTES, null);
|
||||
assertThat(securityContextAttributes).hasSize(3);
|
||||
assertThat(securityContextAttributes).contains(
|
||||
entry(HttpServletRequest.class, this.servletRequest),
|
||||
assertThat(securityContextAttributes).contains(entry(HttpServletRequest.class, this.servletRequest),
|
||||
entry(HttpServletResponse.class, this.servletResponse),
|
||||
entry(Authentication.class, this.authentication));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void createSubscriberIfNecessaryWhenParentContextContainsSecurityContextAttributesThenUseParentContext() {
|
||||
RequestContextHolder.setRequestAttributes(
|
||||
new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
RequestContextHolder
|
||||
.setRequestAttributes(new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
SecurityContextHolder.getContext().setAuthentication(this.authentication);
|
||||
|
||||
Context parentContext = Context.of(SECURITY_CONTEXT_ATTRIBUTES, new HashMap<>());
|
||||
@@ -143,76 +146,75 @@ public class SecurityReactorContextConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void createSubscriberIfNecessaryWhenNotServletRequestAttributesThenStillCreate() {
|
||||
RequestContextHolder.setRequestAttributes(
|
||||
new RequestAttributes() {
|
||||
@Override
|
||||
public Object getAttribute(String name, int scope) {
|
||||
return null;
|
||||
}
|
||||
RequestContextHolder.setRequestAttributes(new RequestAttributes() {
|
||||
@Override
|
||||
public Object getAttribute(String name, int scope) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAttribute(String name, Object value, int scope) {
|
||||
}
|
||||
@Override
|
||||
public void setAttribute(String name, Object value, int scope) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeAttribute(String name, int scope) {
|
||||
}
|
||||
@Override
|
||||
public void removeAttribute(String name, int scope) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public String[] getAttributeNames(int scope) {
|
||||
return new String[0];
|
||||
}
|
||||
@Override
|
||||
public String[] getAttributeNames(int scope) {
|
||||
return new String[0];
|
||||
}
|
||||
|
||||
@Override
|
||||
public void registerDestructionCallback(String name, Runnable callback, int scope) {
|
||||
}
|
||||
@Override
|
||||
public void registerDestructionCallback(String name, Runnable callback, int scope) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object resolveReference(String key) {
|
||||
return null;
|
||||
}
|
||||
@Override
|
||||
public Object resolveReference(String key) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSessionId() {
|
||||
return null;
|
||||
}
|
||||
@Override
|
||||
public String getSessionId() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getSessionMutex() {
|
||||
return null;
|
||||
}
|
||||
});
|
||||
@Override
|
||||
public Object getSessionMutex() {
|
||||
return null;
|
||||
}
|
||||
});
|
||||
|
||||
CoreSubscriber<Object> subscriber = this.subscriberRegistrar.createSubscriberIfNecessary(Operators.emptySubscriber());
|
||||
CoreSubscriber<Object> subscriber = this.subscriberRegistrar
|
||||
.createSubscriberIfNecessary(Operators.emptySubscriber());
|
||||
assertThat(subscriber).isInstanceOf(SecurityReactorContextConfiguration.SecurityReactorContextSubscriber.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void createPublisherWhenLastOperatorAddedThenSecurityContextAttributesAvailable() {
|
||||
// Trigger the importing of SecurityReactorContextConfiguration via OAuth2ImportSelector
|
||||
// Trigger the importing of SecurityReactorContextConfiguration via
|
||||
// OAuth2ImportSelector
|
||||
this.spring.register(SecurityConfig.class).autowire();
|
||||
|
||||
// Setup for SecurityReactorContextSubscriberRegistrar
|
||||
RequestContextHolder.setRequestAttributes(
|
||||
new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
RequestContextHolder
|
||||
.setRequestAttributes(new ServletRequestAttributes(this.servletRequest, this.servletResponse));
|
||||
SecurityContextHolder.getContext().setAuthentication(this.authentication);
|
||||
|
||||
ClientResponse clientResponseOk = ClientResponse.create(HttpStatus.OK).build();
|
||||
|
||||
ExchangeFilterFunction filter = (req, next) ->
|
||||
Mono.subscriberContext()
|
||||
.filter(ctx -> ctx.hasKey(SECURITY_CONTEXT_ATTRIBUTES))
|
||||
.map(ctx -> ctx.get(SECURITY_CONTEXT_ATTRIBUTES))
|
||||
.cast(Map.class)
|
||||
.map(attributes -> {
|
||||
if (attributes.containsKey(HttpServletRequest.class) &&
|
||||
attributes.containsKey(HttpServletResponse.class) &&
|
||||
attributes.containsKey(Authentication.class)) {
|
||||
return clientResponseOk;
|
||||
} else {
|
||||
return ClientResponse.create(HttpStatus.NOT_FOUND).build();
|
||||
}
|
||||
});
|
||||
ExchangeFilterFunction filter = (req, next) -> Mono.subscriberContext()
|
||||
.filter(ctx -> ctx.hasKey(SECURITY_CONTEXT_ATTRIBUTES)).map(ctx -> ctx.get(SECURITY_CONTEXT_ATTRIBUTES))
|
||||
.cast(Map.class).map(attributes -> {
|
||||
if (attributes.containsKey(HttpServletRequest.class)
|
||||
&& attributes.containsKey(HttpServletResponse.class)
|
||||
&& attributes.containsKey(Authentication.class)) {
|
||||
return clientResponseOk;
|
||||
}
|
||||
else {
|
||||
return ClientResponse.create(HttpStatus.NOT_FOUND).build();
|
||||
}
|
||||
});
|
||||
|
||||
ClientRequest clientRequest = ClientRequest.create(GET, URI.create("https://example.com")).build();
|
||||
MockExchangeFunction exchange = new MockExchangeFunction();
|
||||
@@ -225,11 +227,8 @@ public class SecurityReactorContextConfigurationTests {
|
||||
Mono<ClientResponse> clientResponseMono = filter.filter(clientRequest, exchange)
|
||||
.flatMap(response -> filter.filter(clientRequest, exchange));
|
||||
|
||||
StepVerifier.create(clientResponseMono)
|
||||
.expectAccessibleContext()
|
||||
.contains(SECURITY_CONTEXT_ATTRIBUTES, expectedContextAttributes)
|
||||
.then()
|
||||
.expectNext(clientResponseOk)
|
||||
StepVerifier.create(clientResponseMono).expectAccessibleContext()
|
||||
.contains(SECURITY_CONTEXT_ATTRIBUTES, expectedContextAttributes).then().expectNext(clientResponseOk)
|
||||
.verifyComplete();
|
||||
}
|
||||
|
||||
@@ -239,5 +238,7 @@ public class SecurityReactorContextConfigurationTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -75,8 +75,7 @@ public class WebMvcSecurityConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void authenticationPrincipalResolved() throws Exception {
|
||||
mockMvc.perform(get("/authentication-principal"))
|
||||
.andExpect(assertResult(authentication.getPrincipal()))
|
||||
mockMvc.perform(get("/authentication-principal")).andExpect(assertResult(authentication.getPrincipal()))
|
||||
.andExpect(view().name("authentication-principal-view"));
|
||||
}
|
||||
|
||||
@@ -90,8 +89,7 @@ public class WebMvcSecurityConfigurationTests {
|
||||
@Test
|
||||
public void csrfToken() throws Exception {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("headerName", "paramName", "token");
|
||||
MockHttpServletRequestBuilder request = get("/csrf").requestAttr(
|
||||
CsrfToken.class.getName(), csrfToken);
|
||||
MockHttpServletRequestBuilder request = get("/csrf").requestAttr(CsrfToken.class.getName(), csrfToken);
|
||||
|
||||
mockMvc.perform(request).andExpect(assertResult(csrfToken));
|
||||
}
|
||||
@@ -104,32 +102,33 @@ public class WebMvcSecurityConfigurationTests {
|
||||
static class TestController {
|
||||
|
||||
@RequestMapping("/authentication-principal")
|
||||
public ModelAndView authenticationPrincipal(
|
||||
@AuthenticationPrincipal String principal) {
|
||||
public ModelAndView authenticationPrincipal(@AuthenticationPrincipal String principal) {
|
||||
return new ModelAndView("authentication-principal-view", "result", principal);
|
||||
}
|
||||
|
||||
@RequestMapping("/deprecated-authentication-principal")
|
||||
public ModelAndView deprecatedAuthenticationPrincipal(
|
||||
@org.springframework.security.web.bind.annotation.AuthenticationPrincipal String principal) {
|
||||
return new ModelAndView("deprecated-authentication-principal-view", "result",
|
||||
principal);
|
||||
return new ModelAndView("deprecated-authentication-principal-view", "result", principal);
|
||||
}
|
||||
|
||||
@RequestMapping("/csrf")
|
||||
public ModelAndView csrf(CsrfToken token) {
|
||||
return new ModelAndView("view", "result", token);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
@EnableWebSecurity
|
||||
static class Config {
|
||||
|
||||
@Bean
|
||||
public TestController testController() {
|
||||
return new TestController();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -74,6 +74,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Evgeniy Cheban
|
||||
*/
|
||||
public class WebSecurityConfigurationTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -118,11 +119,10 @@ public class WebSecurityConfigurationTests {
|
||||
@Configuration
|
||||
@Order(1)
|
||||
static class WebConfigurer1 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web
|
||||
.ignoring()
|
||||
.antMatchers("/ignore1", "/ignore2");
|
||||
web.ignoring().antMatchers("/ignore1", "/ignore2");
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -134,11 +134,13 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("1");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Order(2)
|
||||
static class WebConfigurer2 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -148,11 +150,13 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("2");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@Order(3)
|
||||
static class WebConfigurer3 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -162,6 +166,7 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("3");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@@ -175,7 +180,9 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("4");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -208,44 +215,29 @@ public class WebSecurityConfigurationTests {
|
||||
@Order(1)
|
||||
@Bean
|
||||
SecurityFilterChain filterChain1(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.antMatcher("/role1/**")
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().hasRole("1")
|
||||
)
|
||||
return http.antMatcher("/role1/**").authorizeRequests(authorize -> authorize.anyRequest().hasRole("1"))
|
||||
.build();
|
||||
}
|
||||
|
||||
@Order(2)
|
||||
@Bean
|
||||
SecurityFilterChain filterChain2(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.antMatcher("/role2/**")
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().hasRole("2")
|
||||
)
|
||||
return http.antMatcher("/role2/**").authorizeRequests(authorize -> authorize.anyRequest().hasRole("2"))
|
||||
.build();
|
||||
}
|
||||
|
||||
@Order(3)
|
||||
@Bean
|
||||
SecurityFilterChain filterChain3(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.antMatcher("/role3/**")
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().hasRole("3")
|
||||
)
|
||||
return http.antMatcher("/role3/**").authorizeRequests(authorize -> authorize.anyRequest().hasRole("3"))
|
||||
.build();
|
||||
}
|
||||
|
||||
@Bean
|
||||
SecurityFilterChain filterChain4(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().hasRole("4")
|
||||
)
|
||||
.build();
|
||||
return http.authorizeRequests(authorize -> authorize.anyRequest().hasRole("4")).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -253,9 +245,9 @@ public class WebSecurityConfigurationTests {
|
||||
Throwable thrown = catchThrowable(() -> this.spring.register(DuplicateOrderConfig.class).autowire());
|
||||
|
||||
assertThat(thrown).isInstanceOf(BeanCreationException.class)
|
||||
.hasMessageContaining("@Order on WebSecurityConfigurers must be unique")
|
||||
.hasMessageContaining(DuplicateOrderConfig.WebConfigurer1.class.getName())
|
||||
.hasMessageContaining(DuplicateOrderConfig.WebConfigurer2.class.getName());
|
||||
.hasMessageContaining("@Order on WebSecurityConfigurers must be unique")
|
||||
.hasMessageContaining(DuplicateOrderConfig.WebConfigurer1.class.getName())
|
||||
.hasMessageContaining(DuplicateOrderConfig.WebConfigurer2.class.getName());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -264,6 +256,7 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
static class WebConfigurer1 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -273,10 +266,12 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("1");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class WebConfigurer2 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -286,7 +281,9 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().hasRole("2");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -296,32 +293,36 @@ public class WebSecurityConfigurationTests {
|
||||
this.spring.register(PrivilegeEvaluatorConfigurerAdapterConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(WebInvocationPrivilegeEvaluator.class))
|
||||
.isSameAs(PrivilegeEvaluatorConfigurerAdapterConfig.PRIVILEGE_EVALUATOR);
|
||||
.isSameAs(PrivilegeEvaluatorConfigurerAdapterConfig.PRIVILEGE_EVALUATOR);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PrivilegeEvaluatorConfigurerAdapterConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static WebInvocationPrivilegeEvaluator PRIVILEGE_EVALUATOR;
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web.privilegeEvaluator(PRIVILEGE_EVALUATOR);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenSecurityExpressionHandlerSetThenIsRegistered() {
|
||||
WebSecurityExpressionHandlerConfig.EXPRESSION_HANDLER = mock(SecurityExpressionHandler.class);
|
||||
when(WebSecurityExpressionHandlerConfig.EXPRESSION_HANDLER.getExpressionParser()).thenReturn(mock(ExpressionParser.class));
|
||||
when(WebSecurityExpressionHandlerConfig.EXPRESSION_HANDLER.getExpressionParser())
|
||||
.thenReturn(mock(ExpressionParser.class));
|
||||
|
||||
this.spring.register(WebSecurityExpressionHandlerConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(SecurityExpressionHandler.class))
|
||||
.isSameAs(WebSecurityExpressionHandlerConfig.EXPRESSION_HANDLER);
|
||||
.isSameAs(WebSecurityExpressionHandlerConfig.EXPRESSION_HANDLER);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityExpressionHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static SecurityExpressionHandler EXPRESSION_HANDLER;
|
||||
|
||||
@Override
|
||||
@@ -338,13 +339,13 @@ public class WebSecurityConfigurationTests {
|
||||
.expressionHandler(EXPRESSION_HANDLER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenSecurityExpressionHandlerIsNullThenException() {
|
||||
Throwable thrown = catchThrowable(() ->
|
||||
this.spring.register(NullWebSecurityExpressionHandlerConfig.class).autowire()
|
||||
);
|
||||
Throwable thrown = catchThrowable(
|
||||
() -> this.spring.register(NullWebSecurityExpressionHandlerConfig.class).autowire());
|
||||
|
||||
assertThat(thrown).isInstanceOf(BeanCreationException.class);
|
||||
assertThat(thrown).hasRootCauseExactlyInstanceOf(IllegalArgumentException.class);
|
||||
@@ -357,6 +358,7 @@ public class WebSecurityConfigurationTests {
|
||||
public void configure(WebSecurity web) {
|
||||
web.expressionHandler(null);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -364,11 +366,12 @@ public class WebSecurityConfigurationTests {
|
||||
this.spring.register(WebSecurityExpressionHandlerDefaultsConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(SecurityExpressionHandler.class))
|
||||
.isInstanceOf(DefaultWebSecurityExpressionHandler.class);
|
||||
.isInstanceOf(DefaultWebSecurityExpressionHandler.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityExpressionHandlerDefaultsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -377,6 +380,7 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().authenticated();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -386,50 +390,53 @@ public class WebSecurityConfigurationTests {
|
||||
FilterInvocation invocation = new FilterInvocation(new MockHttpServletRequest("GET", ""),
|
||||
new MockHttpServletResponse(), new MockFilterChain());
|
||||
|
||||
AbstractSecurityExpressionHandler handler = this.spring.getContext().getBean(AbstractSecurityExpressionHandler.class);
|
||||
AbstractSecurityExpressionHandler handler = this.spring.getContext()
|
||||
.getBean(AbstractSecurityExpressionHandler.class);
|
||||
EvaluationContext evaluationContext = handler.createEvaluationContext(authentication, invocation);
|
||||
Expression expression = handler.getExpressionParser()
|
||||
.parseExpression("hasRole('ROLE_USER')");
|
||||
Expression expression = handler.getExpressionParser().parseExpression("hasRole('ROLE_USER')");
|
||||
boolean granted = expression.getValue(evaluationContext, Boolean.class);
|
||||
assertThat(granted).isTrue();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityExpressionHandlerRoleHierarchyBeanConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Bean
|
||||
RoleHierarchy roleHierarchy() {
|
||||
RoleHierarchyImpl roleHierarchy = new RoleHierarchyImpl();
|
||||
roleHierarchy.setHierarchy("ROLE_ADMIN > ROLE_USER");
|
||||
return roleHierarchy;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void securityExpressionHandlerWhenPermissionEvaluatorBeanThenPermissionEvaluatorUsed() {
|
||||
this.spring.register(WebSecurityExpressionHandlerPermissionEvaluatorBeanConfig.class).autowire();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("user", "notused");
|
||||
FilterInvocation invocation = new FilterInvocation(new MockHttpServletRequest("GET", ""), new MockHttpServletResponse(), new MockFilterChain());
|
||||
FilterInvocation invocation = new FilterInvocation(new MockHttpServletRequest("GET", ""),
|
||||
new MockHttpServletResponse(), new MockFilterChain());
|
||||
|
||||
AbstractSecurityExpressionHandler handler = this.spring.getContext().getBean(AbstractSecurityExpressionHandler.class);
|
||||
AbstractSecurityExpressionHandler handler = this.spring.getContext()
|
||||
.getBean(AbstractSecurityExpressionHandler.class);
|
||||
EvaluationContext evaluationContext = handler.createEvaluationContext(authentication, invocation);
|
||||
Expression expression = handler.getExpressionParser()
|
||||
.parseExpression("hasPermission(#study,'DELETE')");
|
||||
Expression expression = handler.getExpressionParser().parseExpression("hasPermission(#study,'DELETE')");
|
||||
boolean granted = expression.getValue(evaluationContext, Boolean.class);
|
||||
assertThat(granted).isTrue();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityExpressionHandlerPermissionEvaluatorBeanConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static final PermissionEvaluator PERMIT_ALL_PERMISSION_EVALUATOR = new PermissionEvaluator() {
|
||||
@Override
|
||||
public boolean hasPermission(Authentication authentication,
|
||||
Object targetDomainObject, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject, Object permission) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(Authentication authentication,
|
||||
Serializable targetId, String targetType, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Serializable targetId, String targetType,
|
||||
Object permission) {
|
||||
return true;
|
||||
}
|
||||
};
|
||||
@@ -438,6 +445,7 @@ public class WebSecurityConfigurationTests {
|
||||
public PermissionEvaluator permissionEvaluator() {
|
||||
return PERMIT_ALL_PERMISSION_EVALUATOR;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -445,11 +453,12 @@ public class WebSecurityConfigurationTests {
|
||||
this.spring.register(WebInvocationPrivilegeEvaluatorDefaultsConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(WebInvocationPrivilegeEvaluator.class))
|
||||
.isInstanceOf(DefaultWebInvocationPrivilegeEvaluator.class);
|
||||
.isInstanceOf(DefaultWebInvocationPrivilegeEvaluator.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebInvocationPrivilegeEvaluatorDefaultsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -458,6 +467,7 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().authenticated();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -465,19 +475,17 @@ public class WebSecurityConfigurationTests {
|
||||
this.spring.register(AuthorizeRequestsFilterChainConfig.class).autowire();
|
||||
|
||||
assertThat(this.spring.getContext().getBean(WebInvocationPrivilegeEvaluator.class))
|
||||
.isInstanceOf(DefaultWebInvocationPrivilegeEvaluator.class);
|
||||
.isInstanceOf(DefaultWebInvocationPrivilegeEvaluator.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthorizeRequestsFilterChainConfig {
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().authenticated()
|
||||
)
|
||||
.build();
|
||||
return http.authorizeRequests(authorize -> authorize.anyRequest().authenticated()).build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2303
|
||||
@@ -491,6 +499,7 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultExpressionHandlerSetsBeanResolverConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -502,10 +511,12 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@RestController
|
||||
public class HomeController {
|
||||
|
||||
@GetMapping("/")
|
||||
public String home() {
|
||||
return "home";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Bean
|
||||
@@ -514,6 +525,7 @@ public class WebSecurityConfigurationTests {
|
||||
}
|
||||
|
||||
static class MyBean {
|
||||
|
||||
public boolean deny() {
|
||||
return false;
|
||||
}
|
||||
@@ -521,7 +533,9 @@ public class WebSecurityConfigurationTests {
|
||||
public boolean grant() {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Rule
|
||||
@@ -545,14 +559,17 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ParentConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ChildConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
// SEC-2773
|
||||
@@ -564,7 +581,8 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void loadConfigWhenBeanProxyingEnabledAndSubclassThenFilterChainsCreated() {
|
||||
this.spring.register(GlobalAuthenticationWebSecurityConfigurerAdaptersConfig.class, SubclassConfig.class).autowire();
|
||||
this.spring.register(GlobalAuthenticationWebSecurityConfigurerAdaptersConfig.class, SubclassConfig.class)
|
||||
.autowire();
|
||||
|
||||
FilterChainProxy filterChainProxy = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
List<SecurityFilterChain> filterChains = filterChainProxy.getFilterChains();
|
||||
@@ -574,19 +592,20 @@ public class WebSecurityConfigurationTests {
|
||||
|
||||
@Configuration
|
||||
static class SubclassConfig extends WebSecurityConfiguration {
|
||||
|
||||
}
|
||||
|
||||
@Import(AuthenticationTestConfiguration.class)
|
||||
@EnableGlobalAuthentication
|
||||
static class GlobalAuthenticationWebSecurityConfigurerAdaptersConfig {
|
||||
|
||||
@Configuration
|
||||
@Order(1)
|
||||
static class WebConfigurer1 extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
web
|
||||
.ignoring()
|
||||
.antMatchers("/ignore1", "/ignore2");
|
||||
web.ignoring().antMatchers("/ignore1", "/ignore2");
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -598,6 +617,7 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().anonymous();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@@ -611,7 +631,9 @@ public class WebSecurityConfigurationTests {
|
||||
.anyRequest().authenticated();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -627,28 +649,25 @@ public class WebSecurityConfigurationTests {
|
||||
@EnableWebSecurity
|
||||
@Import(AuthenticationTestConfiguration.class)
|
||||
static class AdapterAndFilterChainConfig {
|
||||
|
||||
@Order(1)
|
||||
@Configuration
|
||||
static class WebConfigurer extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
http
|
||||
.antMatcher("/config/**")
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().permitAll()
|
||||
);
|
||||
http.antMatcher("/config/**").authorizeRequests(authorize -> authorize.anyRequest().permitAll());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Order(2)
|
||||
@Bean
|
||||
SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
|
||||
return http
|
||||
.antMatcher("/filter/**")
|
||||
.authorizeRequests(authorize -> authorize
|
||||
.anyRequest().authenticated()
|
||||
)
|
||||
return http.antMatcher("/filter/**").authorizeRequests(authorize -> authorize.anyRequest().authenticated())
|
||||
.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -38,10 +38,10 @@ public class Sec2377Tests {
|
||||
public void refreshContextWhenParentAndChildRegisteredThenNoException() {
|
||||
this.parent.register(Sec2377AConfig.class).autowire();
|
||||
|
||||
ConfigurableApplicationContext context =
|
||||
this.child.register(Sec2377BConfig.class).getContext();
|
||||
ConfigurableApplicationContext context = this.child.register(Sec2377BConfig.class).getContext();
|
||||
context.setParent(this.parent.getContext());
|
||||
|
||||
this.child.autowire();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
import java.util.List;
|
||||
|
||||
public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
|
||||
private ConcreteAbstractRequestMatcherMappingConfigurer registry;
|
||||
|
||||
@Before
|
||||
@@ -37,7 +38,7 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetRequestMatcherIsTypeRegexMatcher(){
|
||||
public void testGetRequestMatcherIsTypeRegexMatcher() {
|
||||
List<RequestMatcher> requestMatchers = registry.regexMatchers(HttpMethod.GET, "/a.*");
|
||||
|
||||
for (RequestMatcher requestMatcher : requestMatchers) {
|
||||
@@ -46,8 +47,8 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testRequestMatcherIsTypeRegexMatcher(){
|
||||
List<RequestMatcher> requestMatchers = registry.regexMatchers( "/a.*");
|
||||
public void testRequestMatcherIsTypeRegexMatcher() {
|
||||
List<RequestMatcher> requestMatchers = registry.regexMatchers("/a.*");
|
||||
|
||||
for (RequestMatcher requestMatcher : requestMatchers) {
|
||||
assertThat(requestMatcher).isInstanceOf(RegexRequestMatcher.class);
|
||||
@@ -55,7 +56,7 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetRequestMatcherIsTypeAntPathRequestMatcher(){
|
||||
public void testGetRequestMatcherIsTypeAntPathRequestMatcher() {
|
||||
List<RequestMatcher> requestMatchers = registry.antMatchers(HttpMethod.GET, "/a.*");
|
||||
|
||||
for (RequestMatcher requestMatcher : requestMatchers) {
|
||||
@@ -64,7 +65,7 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testRequestMatcherIsTypeAntPathRequestMatcher(){
|
||||
public void testRequestMatcherIsTypeAntPathRequestMatcher() {
|
||||
List<RequestMatcher> requestMatchers = registry.antMatchers("/a.*");
|
||||
|
||||
for (RequestMatcher requestMatcher : requestMatchers) {
|
||||
@@ -72,7 +73,9 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
}
|
||||
}
|
||||
|
||||
static class ConcreteAbstractRequestMatcherMappingConfigurer extends AbstractConfigAttributeRequestMatcherRegistry<List<RequestMatcher>> {
|
||||
static class ConcreteAbstractRequestMatcherMappingConfigurer
|
||||
extends AbstractConfigAttributeRequestMatcherRegistry<List<RequestMatcher>> {
|
||||
|
||||
List<AccessDecisionVoter> decisionVoters() {
|
||||
return null;
|
||||
}
|
||||
@@ -88,5 +91,7 @@ public class AbstractConfigAttributeRequestMatcherRegistryTests {
|
||||
public List<RequestMatcher> mvcMatchers(HttpMethod method, String... mvcPatterns) {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -40,6 +40,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
public class AnonymousConfigurerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -50,8 +51,7 @@ public class AnonymousConfigurerTests {
|
||||
public void requestWhenAnonymousTwiceInvokedThenDoesNotOverride() throws Exception {
|
||||
this.spring.register(InvokeTwiceDoesNotOverride.class, PrincipalController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(content().string("principal"));
|
||||
this.mockMvc.perform(get("/")).andExpect(content().string("principal"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -69,14 +69,14 @@ public class AnonymousConfigurerTests {
|
||||
.anonymous();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenAnonymousPrincipalInLambdaThenPrincipalUsed() throws Exception {
|
||||
this.spring.register(AnonymousPrincipalInLambdaConfig.class, PrincipalController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(content().string("principal"));
|
||||
this.mockMvc.perform(get("/")).andExpect(content().string("principal"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -93,18 +93,19 @@ public class AnonymousConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenAnonymousDisabledInLambdaThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(AnonymousDisabledInLambdaConfig.class, PrincipalController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mockMvc.perform(get("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousDisabledInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -124,18 +125,19 @@ public class AnonymousConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenAnonymousWithDefaultsInLambdaThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(AnonymousWithDefaultsInLambdaConfig.class, PrincipalController.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mockMvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousWithDefaultsInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -155,13 +157,17 @@ public class AnonymousConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class PrincipalController {
|
||||
|
||||
@GetMapping("/")
|
||||
String principal(@AuthenticationPrincipal String principal) {
|
||||
return principal;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -58,11 +58,15 @@ import static org.springframework.security.config.Customizer.withDefaults;
|
||||
*
|
||||
*/
|
||||
public class AuthorizeRequestsTests {
|
||||
|
||||
AnnotationConfigWebApplicationContext context;
|
||||
|
||||
MockHttpServletRequest request;
|
||||
|
||||
MockHttpServletResponse response;
|
||||
|
||||
MockFilterChain chain;
|
||||
|
||||
MockServletContext servletContext;
|
||||
|
||||
@Autowired
|
||||
@@ -98,6 +102,7 @@ public class AuthorizeRequestsTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntMatchersNoPatternsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -114,6 +119,7 @@ public class AuthorizeRequestsTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -129,6 +135,7 @@ public class AuthorizeRequestsTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntMatchersNoPatternsInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -147,6 +154,7 @@ public class AuthorizeRequestsTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2256
|
||||
@@ -190,6 +198,7 @@ public class AuthorizeRequestsTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntPatchersPathVariables extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -207,6 +216,7 @@ public class AuthorizeRequestsTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-3786
|
||||
@@ -231,6 +241,7 @@ public class AuthorizeRequestsTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntMatchersPathVariablesCamelCaseVariables extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -248,6 +259,7 @@ public class AuthorizeRequestsTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// gh-3394
|
||||
@@ -256,8 +268,10 @@ public class AuthorizeRequestsTests {
|
||||
loadConfig(RoleHiearchyConfig.class);
|
||||
|
||||
SecurityContext securityContext = new SecurityContextImpl();
|
||||
securityContext.setAuthentication(new UsernamePasswordAuthenticationToken("test", "notused", AuthorityUtils.createAuthorityList("ROLE_USER")));
|
||||
this.request.getSession().setAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY, securityContext);
|
||||
securityContext.setAuthentication(new UsernamePasswordAuthenticationToken("test", "notused",
|
||||
AuthorityUtils.createAuthorityList("ROLE_USER")));
|
||||
this.request.getSession().setAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY,
|
||||
securityContext);
|
||||
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
@@ -267,6 +281,7 @@ public class AuthorizeRequestsTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class RoleHiearchyConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -290,6 +305,7 @@ public class AuthorizeRequestsTests {
|
||||
result.setHierarchy("ROLE_USER > ROLE_ADMIN");
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -299,30 +315,28 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setRequestURI("/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -343,11 +357,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -357,30 +374,28 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setRequestURI("/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -403,11 +418,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -418,8 +436,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -427,8 +444,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -436,8 +452,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -460,6 +475,7 @@ public class AuthorizeRequestsTests {
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherServletPathConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -480,11 +496,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -495,8 +514,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -504,8 +522,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -513,8 +530,7 @@ public class AuthorizeRequestsTests {
|
||||
this.request.setRequestURI("/spring/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -537,6 +553,7 @@ public class AuthorizeRequestsTests {
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherServletPathInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -559,11 +576,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -581,14 +601,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherPathVariablesConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -609,11 +629,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -631,14 +654,14 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherPathVariablesInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -661,17 +684,21 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherPathServletPathRequiredConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -692,19 +719,24 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class LegacyMvcMatchingConfig implements WebMvcConfigurer {
|
||||
|
||||
@Override
|
||||
public void configurePathMatch(PathMatchConfigurer configurer) {
|
||||
configurer.setUseSuffixPatternMatch(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void loadConfig(Class<?>... configs) {
|
||||
@@ -715,4 +747,5 @@ public class AuthorizeRequestsTests {
|
||||
|
||||
this.context.getAutowireCapableBeanFactory().autowireBean(this);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -56,8 +56,7 @@ public class ChannelSecurityConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(InsecureChannelProcessor.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(InsecureChannelProcessor.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -65,8 +64,7 @@ public class ChannelSecurityConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(SecureChannelProcessor.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(SecureChannelProcessor.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -74,8 +72,7 @@ public class ChannelSecurityConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(ChannelDecisionManagerImpl.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(ChannelDecisionManagerImpl.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -83,12 +80,12 @@ public class ChannelSecurityConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(ChannelProcessingFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(ChannelProcessingFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor;
|
||||
|
||||
@Override
|
||||
@@ -104,21 +101,23 @@ public class ChannelSecurityConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requiresChannelWhenInvokesTwiceThenUsesOriginalRequiresSecure() throws Exception {
|
||||
this.spring.register(DuplicateInvocationsDoesNotOverrideConfig.class).autowire();
|
||||
|
||||
mvc.perform(get("/"))
|
||||
.andExpect(redirectedUrl("https://localhost/"));
|
||||
mvc.perform(get("/")).andExpect(redirectedUrl("https://localhost/"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -134,14 +133,14 @@ public class ChannelSecurityConfigurerTests {
|
||||
.requiresChannel();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenRequiresChannelConfiguredInLambdaThenRedirectsToHttps() throws Exception {
|
||||
this.spring.register(RequiresChannelInLambdaConfig.class).autowire();
|
||||
|
||||
mvc.perform(get("/"))
|
||||
.andExpect(redirectedUrl("https://localhost/"));
|
||||
mvc.perform(get("/")).andExpect(redirectedUrl("https://localhost/"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -157,5 +156,7 @@ public class ChannelSecurityConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -55,6 +55,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Eleftheria Stein
|
||||
*/
|
||||
public class CorsConfigurerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -64,8 +65,8 @@ public class CorsConfigurerTests {
|
||||
@Test
|
||||
public void configureWhenNoMvcThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(DefaultCorsConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasMessageContaining("Please ensure Spring Security & Spring MVC are configured in a shared ApplicationContext");
|
||||
.isInstanceOf(BeanCreationException.class).hasMessageContaining(
|
||||
"Please ensure Spring Security & Spring MVC are configured in a shared ApplicationContext");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -81,14 +82,14 @@ public class CorsConfigurerTests {
|
||||
.cors();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCrossOriginAnnotationThenRespondsWithCorsHeaders() throws Exception {
|
||||
this.spring.register(MvcCorsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -99,8 +100,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -121,23 +121,23 @@ public class CorsConfigurerTests {
|
||||
}
|
||||
|
||||
@RestController
|
||||
@CrossOrigin(methods = {
|
||||
RequestMethod.GET, RequestMethod.POST
|
||||
})
|
||||
@CrossOrigin(methods = { RequestMethod.GET, RequestMethod.POST })
|
||||
static class CorsController {
|
||||
|
||||
@RequestMapping("/")
|
||||
String hello() {
|
||||
return "Hello";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenDefaultsInLambdaAndCrossOriginAnnotationThenRespondsWithCorsHeaders() throws Exception {
|
||||
this.spring.register(MvcCorsInLambdaConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -148,8 +148,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -171,23 +170,23 @@ public class CorsConfigurerTests {
|
||||
}
|
||||
|
||||
@RestController
|
||||
@CrossOrigin(methods = {
|
||||
RequestMethod.GET, RequestMethod.POST
|
||||
})
|
||||
@CrossOrigin(methods = { RequestMethod.GET, RequestMethod.POST })
|
||||
static class CorsController {
|
||||
|
||||
@RequestMapping("/")
|
||||
String hello() {
|
||||
return "Hello";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCorsConfigurationSourceBeanThenRespondsWithCorsHeaders() throws Exception {
|
||||
this.spring.register(ConfigSourceConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -198,8 +197,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -223,12 +221,11 @@ public class CorsConfigurerTests {
|
||||
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
|
||||
CorsConfiguration corsConfiguration = new CorsConfiguration();
|
||||
corsConfiguration.setAllowedOrigins(Collections.singletonList("*"));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(
|
||||
RequestMethod.GET.name(),
|
||||
RequestMethod.POST.name()));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(RequestMethod.GET.name(), RequestMethod.POST.name()));
|
||||
source.registerCorsConfiguration("/**", corsConfiguration);
|
||||
return source;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -236,8 +233,7 @@ public class CorsConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(ConfigSourceInLambdaConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -249,8 +245,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -275,20 +270,18 @@ public class CorsConfigurerTests {
|
||||
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
|
||||
CorsConfiguration corsConfiguration = new CorsConfiguration();
|
||||
corsConfiguration.setAllowedOrigins(Collections.singletonList("*"));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(
|
||||
RequestMethod.GET.name(),
|
||||
RequestMethod.POST.name()));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(RequestMethod.GET.name(), RequestMethod.POST.name()));
|
||||
source.registerCorsConfiguration("/**", corsConfiguration);
|
||||
return source;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCorsFilterBeanThenRespondsWithCorsHeaders() throws Exception {
|
||||
this.spring.register(CorsFilterConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -299,8 +292,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -324,20 +316,18 @@ public class CorsConfigurerTests {
|
||||
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
|
||||
CorsConfiguration corsConfiguration = new CorsConfiguration();
|
||||
corsConfiguration.setAllowedOrigins(Collections.singletonList("*"));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(
|
||||
RequestMethod.GET.name(),
|
||||
RequestMethod.POST.name()));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(RequestMethod.GET.name(), RequestMethod.POST.name()));
|
||||
source.registerCorsConfiguration("/**", corsConfiguration);
|
||||
return new CorsFilter(source);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenConfigSourceInLambdaConfigAndCorsFilterBeanThenRespondsWithCorsHeaders() throws Exception {
|
||||
this.spring.register(CorsFilterInLambdaConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -348,8 +338,7 @@ public class CorsConfigurerTests {
|
||||
|
||||
this.mvc.perform(options("/")
|
||||
.header(org.springframework.http.HttpHeaders.ACCESS_CONTROL_REQUEST_METHOD, HttpMethod.POST.name())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com"))
|
||||
.andExpect(status().isOk())
|
||||
.header(HttpHeaders.ORIGIN, "https://example.com")).andExpect(status().isOk())
|
||||
.andExpect(header().exists("Access-Control-Allow-Origin"))
|
||||
.andExpect(header().exists("X-Content-Type-Options"));
|
||||
}
|
||||
@@ -374,11 +363,11 @@ public class CorsConfigurerTests {
|
||||
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
|
||||
CorsConfiguration corsConfiguration = new CorsConfiguration();
|
||||
corsConfiguration.setAllowedOrigins(Collections.singletonList("*"));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(
|
||||
RequestMethod.GET.name(),
|
||||
RequestMethod.POST.name()));
|
||||
corsConfiguration.setAllowedMethods(Arrays.asList(RequestMethod.GET.name(), RequestMethod.POST.name()));
|
||||
source.registerCorsConfiguration("/**", corsConfiguration);
|
||||
return new CorsFilter(source);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -48,21 +48,18 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@Test
|
||||
public void requestWhenIgnoringRequestMatchersThenAugmentedByConfiguredRequestMatcher()
|
||||
throws Exception {
|
||||
public void requestWhenIgnoringRequestMatchersThenAugmentedByConfiguredRequestMatcher() throws Exception {
|
||||
this.spring.register(IgnoringRequestMatchers.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/path"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/path")).andExpect(status().isForbidden());
|
||||
|
||||
this.mvc.perform(post("/path"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/path")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IgnoringRequestMatchers extends WebSecurityConfigurerAdapter {
|
||||
RequestMatcher requestMatcher =
|
||||
request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
RequestMatcher requestMatcher = request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -73,24 +70,22 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
.ignoringRequestMatchers(this.requestMatcher);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenIgnoringRequestMatchersInLambdaThenAugmentedByConfiguredRequestMatcher()
|
||||
throws Exception {
|
||||
public void requestWhenIgnoringRequestMatchersInLambdaThenAugmentedByConfiguredRequestMatcher() throws Exception {
|
||||
this.spring.register(IgnoringRequestInLambdaMatchers.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/path"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/path")).andExpect(status().isForbidden());
|
||||
|
||||
this.mvc.perform(post("/path"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/path")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IgnoringRequestInLambdaMatchers extends WebSecurityConfigurerAdapter {
|
||||
RequestMatcher requestMatcher =
|
||||
request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
RequestMatcher requestMatcher = request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -103,28 +98,25 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenIgnoringRequestMatcherThenUnionsWithConfiguredIgnoringAntMatchers()
|
||||
throws Exception {
|
||||
public void requestWhenIgnoringRequestMatcherThenUnionsWithConfiguredIgnoringAntMatchers() throws Exception {
|
||||
|
||||
this.spring.register(IgnoringPathsAndMatchers.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(put("/csrf"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(put("/csrf")).andExpect(status().isForbidden());
|
||||
|
||||
this.mvc.perform(post("/csrf"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/csrf")).andExpect(status().isOk());
|
||||
|
||||
this.mvc.perform(put("/no-csrf"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(put("/no-csrf")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IgnoringPathsAndMatchers extends WebSecurityConfigurerAdapter {
|
||||
RequestMatcher requestMatcher =
|
||||
request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
RequestMatcher requestMatcher = request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -135,6 +127,7 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
.ignoringRequestMatchers(this.requestMatcher);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -143,20 +136,17 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
|
||||
this.spring.register(IgnoringPathsAndMatchersInLambdaConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(put("/csrf"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(put("/csrf")).andExpect(status().isForbidden());
|
||||
|
||||
this.mvc.perform(post("/csrf"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/csrf")).andExpect(status().isOk());
|
||||
|
||||
this.mvc.perform(put("/no-csrf"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(put("/no-csrf")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IgnoringPathsAndMatchersInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
RequestMatcher requestMatcher =
|
||||
request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
RequestMatcher requestMatcher = request -> HttpMethod.POST.name().equals(request.getMethod());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -169,10 +159,12 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
public static class BasicController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
@@ -187,5 +179,7 @@ public class CsrfConfigurerIgnoringRequestMatchersTests {
|
||||
public String noCsrf() {
|
||||
return "no-csrf";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -36,6 +36,7 @@ import org.springframework.web.servlet.support.RequestDataValueProcessor;
|
||||
*
|
||||
*/
|
||||
public class CsrfConfigurerNoWebMvcTests {
|
||||
|
||||
ConfigurableApplicationContext context;
|
||||
|
||||
@After
|
||||
@@ -73,15 +74,18 @@ public class CsrfConfigurerNoWebMvcTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EnableWebOverrideRequestDataConfig {
|
||||
|
||||
@Bean
|
||||
@Primary
|
||||
public RequestDataValueProcessor requestDataValueProcessor() {
|
||||
return mock(RequestDataValueProcessor.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -90,6 +94,7 @@ public class CsrfConfigurerNoWebMvcTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void loadContext(Class<?> configs) {
|
||||
@@ -98,4 +103,5 @@ public class CsrfConfigurerNoWebMvcTests {
|
||||
annotationConfigApplicationContext.refresh();
|
||||
this.context = annotationConfigApplicationContext;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -75,6 +75,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @author Sam Simmons
|
||||
*/
|
||||
public class CsrfConfigurerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -83,83 +84,83 @@ public class CsrfConfigurerTests {
|
||||
|
||||
@Test
|
||||
public void postWhenWebSecurityEnabledThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(post("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(post("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void putWhenWebSecurityEnabledThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(put("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(put("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void patchWhenWebSecurityEnabledThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(patch("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(patch("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deleteWhenWebSecurityEnabledThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(delete("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(delete("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void invalidWhenWebSecurityEnabledThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(request("INVALID", URI.create("/")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(request("INVALID", URI.create("/"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenWebSecurityEnabledThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void headWhenWebSecurityEnabledThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(head("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(head("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void traceWhenWebSecurityEnabledThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(request(HttpMethod.TRACE, "/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(request(HttpMethod.TRACE, "/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void optionsWhenWebSecurityEnabledThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
this.spring
|
||||
.register(CsrfAppliedDefaultConfig.class, AllowHttpMethodsFirewallConfig.class, BasicController.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(options("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(options("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -171,12 +172,14 @@ public class CsrfConfigurerTests {
|
||||
|
||||
@Configuration
|
||||
static class AllowHttpMethodsFirewallConfig {
|
||||
|
||||
@Bean
|
||||
StrictHttpFirewall strictHttpFirewall() {
|
||||
StrictHttpFirewall result = new StrictHttpFirewall();
|
||||
result.setUnsafeAllowAnyHttpMethod(true);
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -185,14 +188,14 @@ public class CsrfConfigurerTests {
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void postWhenCsrfDisabledThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(DisableCsrfConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -206,14 +209,14 @@ public class CsrfConfigurerTests {
|
||||
.disable();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void postWhenCsrfDisabledInLambdaThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(DisableCsrfInLambdaConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -226,6 +229,7 @@ public class CsrfConfigurerTests {
|
||||
.csrf(AbstractHttpConfigurer::disable);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2498
|
||||
@@ -235,11 +239,8 @@ public class CsrfConfigurerTests {
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(post("/to-save")).andReturn();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password")
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession()))
|
||||
.andExpect(status().isFound())
|
||||
this.mvc.perform(post("/login").param("username", "user").param("password", "password")
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession())).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("http://localhost/to-save"));
|
||||
}
|
||||
|
||||
@@ -268,6 +269,7 @@ public class CsrfConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -278,17 +280,13 @@ public class CsrfConfigurerTests {
|
||||
when(CsrfDisablesPostRequestFromRequestCacheConfig.REPO.generateToken(any())).thenReturn(csrfToken);
|
||||
this.spring.register(CsrfDisablesPostRequestFromRequestCacheConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(post("/some-url"))
|
||||
.andReturn();
|
||||
this.mvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password")
|
||||
.with(csrf())
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession()))
|
||||
.andExpect(status().isFound())
|
||||
MvcResult mvcResult = this.mvc.perform(post("/some-url")).andReturn();
|
||||
this.mvc.perform(post("/login").param("username", "user").param("password", "password").with(csrf())
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession())).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
|
||||
verify(CsrfDisablesPostRequestFromRequestCacheConfig.REPO, atLeastOnce()).loadToken(any(HttpServletRequest.class));
|
||||
verify(CsrfDisablesPostRequestFromRequestCacheConfig.REPO, atLeastOnce())
|
||||
.loadToken(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -299,21 +297,18 @@ public class CsrfConfigurerTests {
|
||||
when(CsrfDisablesPostRequestFromRequestCacheConfig.REPO.generateToken(any())).thenReturn(csrfToken);
|
||||
this.spring.register(CsrfDisablesPostRequestFromRequestCacheConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/some-url"))
|
||||
.andReturn();
|
||||
this.mvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password")
|
||||
.with(csrf())
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession()))
|
||||
.andExpect(status().isFound())
|
||||
MvcResult mvcResult = this.mvc.perform(get("/some-url")).andReturn();
|
||||
this.mvc.perform(post("/login").param("username", "user").param("password", "password").with(csrf())
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession())).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("http://localhost/some-url"));
|
||||
|
||||
verify(CsrfDisablesPostRequestFromRequestCacheConfig.REPO, atLeastOnce()).loadToken(any(HttpServletRequest.class));
|
||||
verify(CsrfDisablesPostRequestFromRequestCacheConfig.REPO, atLeastOnce())
|
||||
.loadToken(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CsrfDisablesPostRequestFromRequestCacheConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CsrfTokenRepository REPO;
|
||||
|
||||
@Override
|
||||
@@ -338,6 +333,7 @@ public class CsrfConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2422
|
||||
@@ -345,19 +341,16 @@ public class CsrfConfigurerTests {
|
||||
public void postWhenCsrfEnabledAndSessionIsExpiredThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(InvalidSessionUrlConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(post("/")
|
||||
.param("_csrf", "abc"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/error/sessionError"))
|
||||
.andReturn();
|
||||
MvcResult mvcResult = this.mvc.perform(post("/").param("_csrf", "abc")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/error/sessionError")).andReturn();
|
||||
|
||||
this.mvc.perform(post("/")
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession()))
|
||||
this.mvc.perform(post("/").session((MockHttpSession) mvcResult.getRequest().getSession()))
|
||||
.andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InvalidSessionUrlConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -368,16 +361,15 @@ public class CsrfConfigurerTests {
|
||||
.invalidSessionUrl("/error/sessionError");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requireCsrfProtectionMatcherWhenRequestDoesNotMatchThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RequireCsrfProtectionMatcherConfig.class, BasicController.class).autowire();
|
||||
when(RequireCsrfProtectionMatcherConfig.MATCHER.matches(any()))
|
||||
.thenReturn(false);
|
||||
when(RequireCsrfProtectionMatcherConfig.MATCHER.matches(any())).thenReturn(false);
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -386,12 +378,12 @@ public class CsrfConfigurerTests {
|
||||
when(RequireCsrfProtectionMatcherConfig.MATCHER.matches(any())).thenReturn(true);
|
||||
this.spring.register(RequireCsrfProtectionMatcherConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequireCsrfProtectionMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static RequestMatcher MATCHER;
|
||||
|
||||
@Override
|
||||
@@ -402,17 +394,16 @@ public class CsrfConfigurerTests {
|
||||
.requireCsrfProtectionMatcher(MATCHER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requireCsrfProtectionMatcherInLambdaWhenRequestDoesNotMatchThenRespondsWithOk() throws Exception {
|
||||
RequireCsrfProtectionMatcherInLambdaConfig.MATCHER = mock(RequestMatcher.class);
|
||||
this.spring.register(RequireCsrfProtectionMatcherInLambdaConfig.class, BasicController.class).autowire();
|
||||
when(RequireCsrfProtectionMatcherInLambdaConfig.MATCHER.matches(any()))
|
||||
.thenReturn(false);
|
||||
when(RequireCsrfProtectionMatcherInLambdaConfig.MATCHER.matches(any())).thenReturn(false);
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -421,12 +412,12 @@ public class CsrfConfigurerTests {
|
||||
when(RequireCsrfProtectionMatcherInLambdaConfig.MATCHER.matches(any())).thenReturn(true);
|
||||
this.spring.register(RequireCsrfProtectionMatcherInLambdaConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequireCsrfProtectionMatcherInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static RequestMatcher MATCHER;
|
||||
|
||||
@Override
|
||||
@@ -436,6 +427,7 @@ public class CsrfConfigurerTests {
|
||||
.csrf(csrf -> csrf.requireCsrfProtectionMatcher(MATCHER));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -445,8 +437,7 @@ public class CsrfConfigurerTests {
|
||||
.thenReturn(new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "token"));
|
||||
this.spring.register(CsrfTokenRepositoryConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
verify(CsrfTokenRepositoryConfig.REPO).loadToken(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@@ -455,12 +446,10 @@ public class CsrfConfigurerTests {
|
||||
CsrfTokenRepositoryConfig.REPO = mock(CsrfTokenRepository.class);
|
||||
this.spring.register(CsrfTokenRepositoryConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf())
|
||||
.with(user("user")));
|
||||
this.mvc.perform(post("/logout").with(csrf()).with(user("user")));
|
||||
|
||||
verify(CsrfTokenRepositoryConfig.REPO)
|
||||
.saveToken(isNull(), any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
verify(CsrfTokenRepositoryConfig.REPO).saveToken(isNull(), any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -471,18 +460,16 @@ public class CsrfConfigurerTests {
|
||||
when(CsrfTokenRepositoryConfig.REPO.generateToken(any())).thenReturn(csrfToken);
|
||||
this.spring.register(CsrfTokenRepositoryConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.with(csrf())
|
||||
.param("username", "user")
|
||||
.param("password", "password"))
|
||||
this.mvc.perform(post("/login").with(csrf()).param("username", "user").param("password", "password"))
|
||||
.andExpect(redirectedUrl("/"));
|
||||
|
||||
verify(CsrfTokenRepositoryConfig.REPO)
|
||||
.saveToken(isNull(), any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
verify(CsrfTokenRepositoryConfig.REPO).saveToken(isNull(), any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CsrfTokenRepositoryConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CsrfTokenRepository REPO;
|
||||
|
||||
@Override
|
||||
@@ -504,6 +491,7 @@ public class CsrfConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -513,13 +501,13 @@ public class CsrfConfigurerTests {
|
||||
.thenReturn(new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "token"));
|
||||
this.spring.register(CsrfTokenRepositoryInLambdaConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
verify(CsrfTokenRepositoryInLambdaConfig.REPO).loadToken(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CsrfTokenRepositoryInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CsrfTokenRepository REPO;
|
||||
|
||||
@Override
|
||||
@@ -530,6 +518,7 @@ public class CsrfConfigurerTests {
|
||||
.csrf(csrf -> csrf.csrfTokenRepository(REPO));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -537,15 +526,15 @@ public class CsrfConfigurerTests {
|
||||
AccessDeniedHandlerConfig.DENIED_HANDLER = mock(AccessDeniedHandler.class);
|
||||
this.spring.register(AccessDeniedHandlerConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/")).andExpect(status().isOk());
|
||||
|
||||
verify(AccessDeniedHandlerConfig.DENIED_HANDLER)
|
||||
.handle(any(HttpServletRequest.class), any(HttpServletResponse.class), any());
|
||||
verify(AccessDeniedHandlerConfig.DENIED_HANDLER).handle(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class), any());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AccessDeniedHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AccessDeniedHandler DENIED_HANDLER;
|
||||
|
||||
@Override
|
||||
@@ -556,26 +545,22 @@ public class CsrfConfigurerTests {
|
||||
.accessDeniedHandler(DENIED_HANDLER);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenNoCsrfTokenThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.param("username", "user")
|
||||
.param("password", "password"))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(unauthenticated());
|
||||
this.mvc.perform(post("/login").param("username", "user").param("password", "password"))
|
||||
.andExpect(status().isForbidden()).andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenNoCsrfTokenThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(user("username")))
|
||||
.andExpect(status().isForbidden())
|
||||
this.mvc.perform(post("/logout").with(user("username"))).andExpect(status().isForbidden())
|
||||
.andExpect(authenticated());
|
||||
}
|
||||
|
||||
@@ -584,9 +569,7 @@ public class CsrfConfigurerTests {
|
||||
public void logoutWhenCsrfEnabledAndGetRequestThenDoesNotLogout() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/logout")
|
||||
.with(user("username")))
|
||||
.andExpect(authenticated());
|
||||
this.mvc.perform(get("/logout").with(user("username"))).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -599,15 +582,14 @@ public class CsrfConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenGetRequestAndGetEnabledForLogoutThenLogsOut() throws Exception {
|
||||
this.spring.register(LogoutAllowsGetConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/logout")
|
||||
.with(user("username")))
|
||||
.andExpect(unauthenticated());
|
||||
this.mvc.perform(get("/logout").with(user("username"))).andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -623,18 +605,19 @@ public class CsrfConfigurerTests {
|
||||
.logoutRequestMatcher(new AntPathRequestMatcher("/logout"));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2749
|
||||
@Test
|
||||
public void configureWhenRequireCsrfProtectionMatcherNullThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullRequireCsrfProtectionMatcherConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullRequireCsrfProtectionMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -643,14 +626,14 @@ public class CsrfConfigurerTests {
|
||||
.requireCsrfProtectionMatcher(null);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenDefaultCsrfTokenRepositoryThenDoesNotCreateSession() throws Exception {
|
||||
this.spring.register(DefaultDoesNotCreateSession.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andReturn();
|
||||
MvcResult mvcResult = this.mvc.perform(get("/")).andReturn();
|
||||
|
||||
assertThat(mvcResult.getRequest().getSession(false)).isNull();
|
||||
}
|
||||
@@ -679,10 +662,12 @@ public class CsrfConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullAuthenticationStrategy extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -691,17 +676,18 @@ public class CsrfConfigurerTests {
|
||||
.sessionAuthenticationStrategy(null);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenNullAuthenticationStrategyThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullAuthenticationStrategy.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CsrfAuthenticationStrategyConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static SessionAuthenticationStrategy STRATEGY;
|
||||
|
||||
@Override
|
||||
@@ -723,6 +709,7 @@ public class CsrfConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -731,18 +718,16 @@ public class CsrfConfigurerTests {
|
||||
|
||||
this.spring.register(CsrfAuthenticationStrategyConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.with(csrf())
|
||||
.param("username", "user")
|
||||
.param("password", "password"))
|
||||
this.mvc.perform(post("/login").with(csrf()).param("username", "user").param("password", "password"))
|
||||
.andExpect(redirectedUrl("/"));
|
||||
|
||||
verify(CsrfAuthenticationStrategyConfig.STRATEGY, atLeastOnce())
|
||||
.onAuthentication(any(Authentication.class), any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
verify(CsrfAuthenticationStrategyConfig.STRATEGY, atLeastOnce()).onAuthentication(any(Authentication.class),
|
||||
any(HttpServletRequest.class), any(HttpServletResponse.class));
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class BasicController {
|
||||
|
||||
@GetMapping("/")
|
||||
public void rootGet() {
|
||||
}
|
||||
@@ -750,5 +735,7 @@ public class CsrfConfigurerTests {
|
||||
@PostMapping("/")
|
||||
public void rootPost() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -78,6 +78,7 @@ public class DefaultFiltersTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FilterChainProxyBuilderMissingConfig {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -86,31 +87,36 @@ public class DefaultFiltersTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void nullWebInvocationPrivilegeEvaluator() {
|
||||
this.spring.register(NullWebInvocationPrivilegeEvaluatorConfig.class, UserDetailsServiceConfig.class);
|
||||
List<SecurityFilterChain> filterChains = this.spring.getContext().getBean(FilterChainProxy.class).getFilterChains();
|
||||
List<SecurityFilterChain> filterChains = this.spring.getContext().getBean(FilterChainProxy.class)
|
||||
.getFilterChains();
|
||||
assertThat(filterChains.size()).isEqualTo(1);
|
||||
DefaultSecurityFilterChain filterChain = (DefaultSecurityFilterChain) filterChains.get(0);
|
||||
assertThat(filterChain.getRequestMatcher()).isInstanceOf(AnyRequestMatcher.class);
|
||||
assertThat(filterChain.getFilters().size()).isEqualTo(1);
|
||||
long filter = filterChain.getFilters().stream()
|
||||
.filter(it -> it instanceof UsernamePasswordAuthenticationFilter).count();
|
||||
long filter = filterChain.getFilters().stream().filter(it -> it instanceof UsernamePasswordAuthenticationFilter)
|
||||
.count();
|
||||
assertThat(filter).isEqualTo(1);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class UserDetailsServiceConfig {
|
||||
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
return new InMemoryUserDetailsManager(PasswordEncodedUser.user(), PasswordEncodedUser.admin());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullWebInvocationPrivilegeEvaluatorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
NullWebInvocationPrivilegeEvaluatorConfig() {
|
||||
super(true);
|
||||
}
|
||||
@@ -118,12 +124,14 @@ public class DefaultFiltersTests {
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
http.formLogin();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void filterChainProxyBuilderIgnoringResources() {
|
||||
this.spring.register(FilterChainProxyBuilderIgnoringConfig.class, UserDetailsServiceConfig.class);
|
||||
List<SecurityFilterChain> filterChains = this.spring.getContext().getBean(FilterChainProxy.class).getFilterChains();
|
||||
List<SecurityFilterChain> filterChains = this.spring.getContext().getBean(FilterChainProxy.class)
|
||||
.getFilterChains();
|
||||
assertThat(filterChains.size()).isEqualTo(2);
|
||||
DefaultSecurityFilterChain firstFilter = (DefaultSecurityFilterChain) filterChains.get(0);
|
||||
DefaultSecurityFilterChain secondFilter = (DefaultSecurityFilterChain) filterChains.get(1);
|
||||
@@ -148,6 +156,7 @@ public class DefaultFiltersTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FilterChainProxyBuilderIgnoringConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
// @formatter:off
|
||||
@@ -165,6 +174,7 @@ public class DefaultFiltersTests {
|
||||
.anyRequest().hasRole("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -185,7 +195,10 @@ public class DefaultFiltersTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultFiltersConfigPermitAll extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -68,8 +68,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
public void getWhenFormLoginEnabledThenRedirectsToLoginPage() throws Exception {
|
||||
this.spring.register(DefaultLoginPageConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(redirectedUrl("http://localhost/login"));
|
||||
this.mvc.perform(get("/")).andExpect(redirectedUrl("http://localhost/login"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -78,47 +77,33 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
this.mvc.perform(get("/login")
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form class=\"form-signin\" method=\"post\" action=\"/login\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Please sign in</h2>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Username</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"password\" class=\"sr-only\">Password</label>\n" +
|
||||
" <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n" +
|
||||
" </p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
this.mvc.perform(get("/login").sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form class=\"form-signin\" method=\"post\" action=\"/login\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Please sign in</h2>\n" + " <p>\n"
|
||||
+ " <label for=\"username\" class=\"sr-only\">Username</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + " <p>\n"
|
||||
+ " <label for=\"password\" class=\"sr-only\">Password</label>\n"
|
||||
+ " <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n"
|
||||
+ " </p>\n" + "<input name=\"" + csrfToken.getParameterName()
|
||||
+ "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenNoCredentialsThenRedirectedToLoginPageWithError() throws Exception {
|
||||
this.spring.register(DefaultLoginPageConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.with(csrf()))
|
||||
.andExpect(redirectedUrl("/login?error"));
|
||||
this.mvc.perform(post("/login").with(csrf())).andExpect(redirectedUrl("/login?error"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -127,53 +112,37 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(post("/login")
|
||||
.with(csrf()))
|
||||
.andReturn();
|
||||
MvcResult mvcResult = this.mvc.perform(post("/login").with(csrf())).andReturn();
|
||||
|
||||
this.mvc.perform(get("/login?error")
|
||||
.session((MockHttpSession) mvcResult.getRequest().getSession())
|
||||
this.mvc.perform(get("/login?error").session((MockHttpSession) mvcResult.getRequest().getSession())
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form class=\"form-signin\" method=\"post\" action=\"/login\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Please sign in</h2>\n" +
|
||||
"<div class=\"alert alert-danger\" role=\"alert\">Bad credentials</div> <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Username</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"password\" class=\"sr-only\">Password</label>\n" +
|
||||
" <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n" +
|
||||
" </p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form class=\"form-signin\" method=\"post\" action=\"/login\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Please sign in</h2>\n"
|
||||
+ "<div class=\"alert alert-danger\" role=\"alert\">Bad credentials</div> <p>\n"
|
||||
+ " <label for=\"username\" class=\"sr-only\">Username</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + " <p>\n"
|
||||
+ " <label for=\"password\" class=\"sr-only\">Password</label>\n"
|
||||
+ " <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n"
|
||||
+ " </p>\n" + "<input name=\"" + csrfToken.getParameterName()
|
||||
+ "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenValidCredentialsThenRedirectsToDefaultSuccessPage() throws Exception {
|
||||
this.spring.register(DefaultLoginPageConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/login")
|
||||
.with(csrf())
|
||||
.param("username", "user")
|
||||
.param("password", "password"))
|
||||
this.mvc.perform(post("/login").with(csrf()).param("username", "user").param("password", "password"))
|
||||
.andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@@ -183,42 +152,32 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
this.mvc.perform(get("/login?logout")
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form class=\"form-signin\" method=\"post\" action=\"/login\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Please sign in</h2>\n" +
|
||||
"<div class=\"alert alert-success\" role=\"alert\">You have been signed out</div> <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Username</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"password\" class=\"sr-only\">Password</label>\n" +
|
||||
" <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n" +
|
||||
" </p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
this.mvc.perform(get("/login?logout").sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form class=\"form-signin\" method=\"post\" action=\"/login\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Please sign in</h2>\n"
|
||||
+ "<div class=\"alert alert-success\" role=\"alert\">You have been signed out</div> <p>\n"
|
||||
+ " <label for=\"username\" class=\"sr-only\">Username</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + " <p>\n"
|
||||
+ " <label for=\"password\" class=\"sr-only\">Password</label>\n"
|
||||
+ " <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n"
|
||||
+ " </p>\n" + "<input name=\"" + csrfToken.getParameterName()
|
||||
+ "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -238,19 +197,19 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginPageWhenLoggedOutAndCustomLogoutSuccessHandlerThenDoesNotRenderLoginPage() throws Exception {
|
||||
this.spring.register(DefaultLoginPageCustomLogoutSuccessHandlerConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/login?logout"))
|
||||
.andExpect(content().string(""));
|
||||
this.mvc.perform(get("/login?logout")).andExpect(content().string(""));
|
||||
}
|
||||
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageCustomLogoutSuccessHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -264,18 +223,19 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginPageWhenLoggedOutAndCustomLogoutSuccessUrlThenDoesNotRenderLoginPage() throws Exception {
|
||||
this.spring.register(DefaultLoginPageCustomLogoutSuccessUrlConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/login?logout"))
|
||||
.andExpect(content().string(""));
|
||||
this.mvc.perform(get("/login?logout")).andExpect(content().string(""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageCustomLogoutSuccessUrlConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -289,6 +249,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -297,43 +258,33 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
this.mvc.perform(get("/login")
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form class=\"form-signin\" method=\"post\" action=\"/login\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Please sign in</h2>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Username</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"password\" class=\"sr-only\">Password</label>\n" +
|
||||
" <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n" +
|
||||
" </p>\n" +
|
||||
"<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
this.mvc.perform(get("/login").sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form class=\"form-signin\" method=\"post\" action=\"/login\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Please sign in</h2>\n" + " <p>\n"
|
||||
+ " <label for=\"username\" class=\"sr-only\">Username</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + " <p>\n"
|
||||
+ " <label for=\"password\" class=\"sr-only\">Password</label>\n"
|
||||
+ " <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n"
|
||||
+ " </p>\n"
|
||||
+ "<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n"
|
||||
+ "<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\""
|
||||
+ csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageWithRememberMeConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -346,6 +297,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.rememberMe();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -355,38 +307,28 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
this.mvc.perform(get("/login")
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form name=\"oidf\" class=\"form-signin\" method=\"post\" action=\"/login/openid\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Login with OpenID Identity</h2>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Identity</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"openid_identifier\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
this.mvc.perform(get("/login").sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form name=\"oidf\" class=\"form-signin\" method=\"post\" action=\"/login/openid\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Login with OpenID Identity</h2>\n"
|
||||
+ " <p>\n" + " <label for=\"username\" class=\"sr-only\">Identity</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"openid_identifier\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + "<input name=\"" + csrfToken.getParameterName()
|
||||
+ "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageWithOpenIDConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -397,6 +339,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.openidLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -405,53 +348,43 @@ public class DefaultLoginPageConfigurerTests {
|
||||
CsrfToken csrfToken = new DefaultCsrfToken("X-CSRF-TOKEN", "_csrf", "BaseSpringSpec_CSRFTOKEN");
|
||||
String csrfAttributeName = HttpSessionCsrfTokenRepository.class.getName().concat(".CSRF_TOKEN");
|
||||
|
||||
this.mvc.perform(get("/login")
|
||||
.sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string(
|
||||
"<!DOCTYPE html>\n" +
|
||||
"<html lang=\"en\">\n" +
|
||||
" <head>\n" +
|
||||
" <meta charset=\"utf-8\">\n" +
|
||||
" <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n" +
|
||||
" <meta name=\"description\" content=\"\">\n" +
|
||||
" <meta name=\"author\" content=\"\">\n" +
|
||||
" <title>Please sign in</title>\n" +
|
||||
" <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n" +
|
||||
" <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n" +
|
||||
" </head>\n" +
|
||||
" <body>\n" +
|
||||
" <div class=\"container\">\n" +
|
||||
" <form class=\"form-signin\" method=\"post\" action=\"/login\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Please sign in</h2>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Username</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"password\" class=\"sr-only\">Password</label>\n" +
|
||||
" <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n" +
|
||||
" </p>\n" +
|
||||
"<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
" <form name=\"oidf\" class=\"form-signin\" method=\"post\" action=\"/login/openid\">\n" +
|
||||
" <h2 class=\"form-signin-heading\">Login with OpenID Identity</h2>\n" +
|
||||
" <p>\n" +
|
||||
" <label for=\"username\" class=\"sr-only\">Identity</label>\n" +
|
||||
" <input type=\"text\" id=\"username\" name=\"openid_identifier\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n" +
|
||||
" </p>\n" +
|
||||
"<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n" +
|
||||
"<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\"" + csrfToken.getToken() + "\" />\n" +
|
||||
" <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n" +
|
||||
" </form>\n" +
|
||||
"</div>\n" +
|
||||
"</body></html>"
|
||||
));
|
||||
this.mvc.perform(get("/login").sessionAttr(csrfAttributeName, csrfToken))
|
||||
.andExpect(content().string("<!DOCTYPE html>\n" + "<html lang=\"en\">\n" + " <head>\n"
|
||||
+ " <meta charset=\"utf-8\">\n"
|
||||
+ " <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, shrink-to-fit=no\">\n"
|
||||
+ " <meta name=\"description\" content=\"\">\n" + " <meta name=\"author\" content=\"\">\n"
|
||||
+ " <title>Please sign in</title>\n"
|
||||
+ " <link href=\"https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css\" rel=\"stylesheet\" integrity=\"sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M\" crossorigin=\"anonymous\">\n"
|
||||
+ " <link href=\"https://getbootstrap.com/docs/4.0/examples/signin/signin.css\" rel=\"stylesheet\" crossorigin=\"anonymous\"/>\n"
|
||||
+ " </head>\n" + " <body>\n" + " <div class=\"container\">\n"
|
||||
+ " <form class=\"form-signin\" method=\"post\" action=\"/login\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Please sign in</h2>\n" + " <p>\n"
|
||||
+ " <label for=\"username\" class=\"sr-only\">Username</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"username\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n" + " <p>\n"
|
||||
+ " <label for=\"password\" class=\"sr-only\">Password</label>\n"
|
||||
+ " <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control\" placeholder=\"Password\" required>\n"
|
||||
+ " </p>\n"
|
||||
+ "<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n"
|
||||
+ "<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\""
|
||||
+ csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n"
|
||||
+ " <form name=\"oidf\" class=\"form-signin\" method=\"post\" action=\"/login/openid\">\n"
|
||||
+ " <h2 class=\"form-signin-heading\">Login with OpenID Identity</h2>\n"
|
||||
+ " <p>\n" + " <label for=\"username\" class=\"sr-only\">Identity</label>\n"
|
||||
+ " <input type=\"text\" id=\"username\" name=\"openid_identifier\" class=\"form-control\" placeholder=\"Username\" required autofocus>\n"
|
||||
+ " </p>\n"
|
||||
+ "<p><input type='checkbox' name='remember-me'/> Remember me on this computer.</p>\n"
|
||||
+ "<input name=\"" + csrfToken.getParameterName() + "\" type=\"hidden\" value=\""
|
||||
+ csrfToken.getToken() + "\" />\n"
|
||||
+ " <button class=\"btn btn-lg btn-primary btn-block\" type=\"submit\">Sign in</button>\n"
|
||||
+ " </form>\n" + "</div>\n" + "</body></html>"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginPageWithFormLoginOpenIDRememberMeConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -466,6 +399,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.openidLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -474,13 +408,13 @@ public class DefaultLoginPageConfigurerTests {
|
||||
|
||||
FilterChainProxy filterChain = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
assertThat(filterChain.getFilterChains().get(0).getFilters().stream()
|
||||
.filter(filter -> filter.getClass().isAssignableFrom(DefaultLoginPageGeneratingFilter.class))
|
||||
.count())
|
||||
.isZero();
|
||||
.filter(filter -> filter.getClass().isAssignableFrom(DefaultLoginPageGeneratingFilter.class)).count())
|
||||
.isZero();
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultLoginWithCustomAuthenticationEntryPointConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -494,6 +428,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -501,8 +436,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(DefaultLoginPageGeneratingFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(DefaultLoginPageGeneratingFilter.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -519,8 +453,7 @@ public class DefaultLoginPageConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(LoginUrlAuthenticationEntryPoint.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(LoginUrlAuthenticationEntryPoint.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -528,12 +461,12 @@ public class DefaultLoginPageConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(ExceptionTranslationFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(ExceptionTranslationFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor;
|
||||
|
||||
@Override
|
||||
@@ -550,12 +483,16 @@ public class DefaultLoginPageConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -43,6 +43,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@SecurityTestExecutionListeners
|
||||
public class ExceptionHandlingConfigurerAccessDeniedHandlerTests {
|
||||
|
||||
@Autowired
|
||||
MockMvc mvc;
|
||||
|
||||
@@ -51,22 +52,19 @@ public class ExceptionHandlingConfigurerAccessDeniedHandlerTests {
|
||||
|
||||
@Test
|
||||
@WithMockUser(roles = "ANYTHING")
|
||||
public void getWhenAccessDeniedOverriddenThenCustomizesResponseByRequest()
|
||||
throws Exception {
|
||||
public void getWhenAccessDeniedOverriddenThenCustomizesResponseByRequest() throws Exception {
|
||||
this.spring.register(RequestMatcherBasedAccessDeniedHandlerConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/hello"))
|
||||
.andExpect(status().isIAmATeapot());
|
||||
this.mvc.perform(get("/hello")).andExpect(status().isIAmATeapot());
|
||||
|
||||
this.mvc.perform(get("/goodbye"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/goodbye")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherBasedAccessDeniedHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
AccessDeniedHandler teapotDeniedHandler =
|
||||
(request, response, exception) ->
|
||||
response.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
AccessDeniedHandler teapotDeniedHandler = (request, response, exception) -> response
|
||||
.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -84,26 +82,24 @@ public class ExceptionHandlingConfigurerAccessDeniedHandlerTests {
|
||||
AnyRequestMatcher.INSTANCE);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@WithMockUser(roles = "ANYTHING")
|
||||
public void getWhenAccessDeniedOverriddenInLambdaThenCustomizesResponseByRequest()
|
||||
throws Exception {
|
||||
public void getWhenAccessDeniedOverriddenInLambdaThenCustomizesResponseByRequest() throws Exception {
|
||||
this.spring.register(RequestMatcherBasedAccessDeniedHandlerInLambdaConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/hello"))
|
||||
.andExpect(status().isIAmATeapot());
|
||||
this.mvc.perform(get("/hello")).andExpect(status().isIAmATeapot());
|
||||
|
||||
this.mvc.perform(get("/goodbye"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/goodbye")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestMatcherBasedAccessDeniedHandlerInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
AccessDeniedHandler teapotDeniedHandler =
|
||||
(request, response, exception) ->
|
||||
response.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
AccessDeniedHandler teapotDeniedHandler = (request, response, exception) -> response
|
||||
.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -126,26 +122,24 @@ public class ExceptionHandlingConfigurerAccessDeniedHandlerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@WithMockUser(roles = "ANYTHING")
|
||||
public void getWhenAccessDeniedOverriddenByOnlyOneHandlerThenAllRequestsUseThatHandler()
|
||||
throws Exception {
|
||||
public void getWhenAccessDeniedOverriddenByOnlyOneHandlerThenAllRequestsUseThatHandler() throws Exception {
|
||||
this.spring.register(SingleRequestMatcherAccessDeniedHandlerConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/hello"))
|
||||
.andExpect(status().isIAmATeapot());
|
||||
this.mvc.perform(get("/hello")).andExpect(status().isIAmATeapot());
|
||||
|
||||
this.mvc.perform(get("/goodbye"))
|
||||
.andExpect(status().isIAmATeapot());
|
||||
this.mvc.perform(get("/goodbye")).andExpect(status().isIAmATeapot());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class SingleRequestMatcherAccessDeniedHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
AccessDeniedHandler teapotDeniedHandler =
|
||||
(request, response, exception) ->
|
||||
response.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
AccessDeniedHandler teapotDeniedHandler = (request, response, exception) -> response
|
||||
.setStatus(HttpStatus.I_AM_A_TEAPOT.value());
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -160,5 +154,7 @@ public class ExceptionHandlingConfigurerAccessDeniedHandlerTests {
|
||||
new AntPathRequestMatcher("/hello/**"));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -67,12 +67,12 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void configureWhenRegisteringObjectPostProcessorThenInvokedOnExceptionTranslationFilter() {
|
||||
this.spring.register(ObjectPostProcessorConfig.class, DefaultSecurityConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(ExceptionTranslationFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(ExceptionTranslationFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
|
||||
@Override
|
||||
@@ -87,13 +87,16 @@ public class ExceptionHandlingConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -101,8 +104,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsApplicationXhtmlXmlThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_XHTML_XML))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.APPLICATION_XHTML_XML))
|
||||
.andExpect(status().isFound());
|
||||
}
|
||||
|
||||
@@ -111,9 +113,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsImageGifThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.IMAGE_GIF))
|
||||
.andExpect(status().isFound());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.IMAGE_GIF)).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -121,9 +121,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsImageJpgThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.IMAGE_JPEG))
|
||||
.andExpect(status().isFound());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.IMAGE_JPEG)).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -131,9 +129,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsImagePngThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.IMAGE_PNG))
|
||||
.andExpect(status().isFound());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.IMAGE_PNG)).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -141,9 +137,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsTextHtmlThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.TEXT_HTML))
|
||||
.andExpect(status().isFound());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.TEXT_HTML)).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -151,9 +145,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsTextPlainThenRespondsWith302() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.TEXT_PLAIN))
|
||||
.andExpect(status().isFound());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.TEXT_PLAIN)).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
// SEC-2199
|
||||
@@ -161,8 +153,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsApplicationAtomXmlThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_ATOM_XML))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.APPLICATION_ATOM_XML))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -171,8 +162,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsApplicationFormUrlEncodedThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_FORM_URLENCODED))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.APPLICATION_FORM_URLENCODED))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -181,8 +171,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsApplicationJsonThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -191,8 +180,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsApplicationOctetStreamThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_OCTET_STREAM))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.APPLICATION_OCTET_STREAM))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -201,8 +189,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsMultipartFormDataThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.MULTIPART_FORM_DATA))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.MULTIPART_FORM_DATA))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -211,9 +198,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptHeaderIsTextXmlThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.TEXT_XML))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.TEXT_XML)).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
// gh-4831
|
||||
@@ -221,18 +206,15 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptIsAnyThenRespondsWith401() throws Exception {
|
||||
this.spring.register(DefaultSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, MediaType.ALL))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, MediaType.ALL)).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAcceptIsChromeThenRespondsWith302() throws Exception {
|
||||
this.spring.register(DefaultSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT,
|
||||
"text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT,
|
||||
"text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8"))
|
||||
.andExpect(status().isFound());
|
||||
}
|
||||
|
||||
@@ -240,9 +222,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
public void getWhenAcceptIsTextPlainAndXRequestedWithIsXHRThenRespondsWith401() throws Exception {
|
||||
this.spring.register(HttpBasicAndFormLoginEntryPointsConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header("Accept", MediaType.TEXT_PLAIN)
|
||||
.header("X-Requested-With", "XMLHttpRequest"))
|
||||
this.mvc.perform(get("/").header("Accept", MediaType.TEXT_PLAIN).header("X-Requested-With", "XMLHttpRequest"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -284,12 +264,13 @@ public class ExceptionHandlingConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCustomContentNegotiationStrategyThenStrategyIsUsed() throws Exception {
|
||||
this.spring.register(OverrideContentNegotiationStrategySharedObjectConfig.class,
|
||||
DefaultSecurityConfig.class).autowire();
|
||||
this.spring.register(OverrideContentNegotiationStrategySharedObjectConfig.class, DefaultSecurityConfig.class)
|
||||
.autowire();
|
||||
|
||||
this.mvc.perform(get("/"));
|
||||
|
||||
@@ -299,38 +280,39 @@ public class ExceptionHandlingConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class OverrideContentNegotiationStrategySharedObjectConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ContentNegotiationStrategy CNS = mock(ContentNegotiationStrategy.class);
|
||||
|
||||
@Bean
|
||||
public static ContentNegotiationStrategy cns() {
|
||||
return CNS;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenUsingDefaultsAndUnauthenticatedThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(DefaultHttpConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, "bogus/type"))
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, "bogus/type"))
|
||||
.andExpect(redirectedUrl("http://localhost/login"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultHttpConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenDeclaringHttpBasicBeforeFormLoginThenRespondsWith401() throws Exception {
|
||||
this.spring.register(BasicAuthenticationEntryPointBeforeFormLoginConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.header(HttpHeaders.ACCEPT, "bogus/type"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/").header(HttpHeaders.ACCEPT, "bogus/type")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class BasicAuthenticationEntryPointBeforeFormLoginConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -343,6 +325,7 @@ public class ExceptionHandlingConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -351,26 +334,20 @@ public class ExceptionHandlingConfigurerTests {
|
||||
|
||||
this.mvc.perform(get("/"));
|
||||
|
||||
verify(InvokeTwiceDoesNotOverrideConfig.AEP)
|
||||
.commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class), any(AuthenticationException.class));
|
||||
verify(InvokeTwiceDoesNotOverrideConfig.AEP).commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class), any(AuthenticationException.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InvokeTwiceDoesNotOverrideConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationEntryPoint AEP = mock(AuthenticationEntryPoint.class);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:on
|
||||
http
|
||||
.authorizeRequests()
|
||||
.anyRequest().authenticated()
|
||||
.and()
|
||||
.exceptionHandling()
|
||||
.authenticationEntryPoint(AEP)
|
||||
.and()
|
||||
.exceptionHandling();
|
||||
http.authorizeRequests().anyRequest().authenticated().and().exceptionHandling()
|
||||
.authenticationEntryPoint(AEP).and().exceptionHandling();
|
||||
// @formatter:off
|
||||
}
|
||||
}
|
||||
|
||||
@@ -84,13 +84,14 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
@Test
|
||||
public void configureWhenHasRoleStartingWithStringRoleThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(HasRoleStartingWithRoleConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class)
|
||||
.hasMessageContaining("role should not start with 'ROLE_' since it is automatically inserted. Got 'ROLE_USER'");
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class)
|
||||
.hasMessageContaining(
|
||||
"role should not start with 'ROLE_' since it is automatically inserted. Got 'ROLE_USER'");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class HasRoleStartingWithRoleConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -99,18 +100,19 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasRole("ROLE_USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenNoCustomAccessDecisionManagerThenUsesAffirmativeBased() {
|
||||
this.spring.register(NoSpecificAccessDecisionManagerConfig.class).autowire();
|
||||
|
||||
verify(NoSpecificAccessDecisionManagerConfig.objectPostProcessor)
|
||||
.postProcess(any(AffirmativeBased.class));
|
||||
verify(NoSpecificAccessDecisionManagerConfig.objectPostProcessor).postProcess(any(AffirmativeBased.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NoSpecificAccessDecisionManagerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
|
||||
@Override
|
||||
@@ -126,34 +128,37 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenAuthorizedRequestsAndNoRequestsThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NoRequestsConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasMessageContaining("At least one mapping is required (i.e. authorizeRequests().anyRequest().authenticated())");
|
||||
.isInstanceOf(BeanCreationException.class).hasMessageContaining(
|
||||
"At least one mapping is required (i.e. authorizeRequests().anyRequest().authenticated())");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NoRequestsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
.authorizeRequests();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenAnyRequestIncompleteMappingThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(IncompleteMappingConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasMessageContaining("An incomplete mapping was found for ");
|
||||
.isInstanceOf(BeanCreationException.class).hasMessageContaining("An incomplete mapping was found for ");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class IncompleteMappingConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -163,15 +168,14 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAnyAuthorityRoleUserConfiguredAndAuthorityIsRoleUserThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenHasAnyAuthorityRoleUserConfiguredAndAuthorityIsRoleUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserAnyAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@@ -180,22 +184,20 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(RoleUserAnyAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
.andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAnyAuthorityRoleUserConfiguredAndNoAuthorityThenRespondsWithUnauthorized()
|
||||
throws Exception {
|
||||
public void getWhenHasAnyAuthorityRoleUserConfiguredAndNoAuthorityThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(RoleUserAnyAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleUserAnyAuthorityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -206,15 +208,14 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasAnyAuthority("ROLE_USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAuthorityRoleUserConfiguredAndAuthorityIsRoleUserThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenHasAuthorityRoleUserConfiguredAndAuthorityIsRoleUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@@ -223,22 +224,20 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(RoleUserAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
.andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAuthorityRoleUserConfiguredAndNoAuthorityThenRespondsWithUnauthorized()
|
||||
throws Exception {
|
||||
public void getWhenHasAuthorityRoleUserConfiguredAndNoAuthorityThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(RoleUserAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleUserAuthorityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -249,25 +248,22 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasAuthority("ROLE_USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAuthorityRoleUserOrAdminRequiredAndAuthorityIsRoleUserThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenAuthorityRoleUserOrAdminRequiredAndAuthorityIsRoleUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserOrRoleAdminAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_USER"))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAuthorityRoleUserOrAdminRequiredAndAuthorityIsRoleAdminThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenAuthorityRoleUserOrAdminRequiredAndAuthorityIsRoleAdminThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserOrRoleAdminAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_ADMIN"))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@@ -276,22 +272,20 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(RoleUserOrRoleAdminAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").authorities(new SimpleGrantedAuthority("ROLE_OTHER"))))
|
||||
this.mvc.perform(get("/").with(user("user").authorities(new SimpleGrantedAuthority("ROLE_OTHER"))))
|
||||
.andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAuthorityRoleUserOrAdminAuthRequiredAndNoUserThenRespondsWithUnauthorized()
|
||||
throws Exception {
|
||||
public void getWhenAuthorityRoleUserOrAdminAuthRequiredAndNoUserThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(RoleUserOrRoleAdminAuthorityConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleUserOrRoleAdminAuthorityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -302,28 +296,26 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasAnyAuthority("ROLE_USER", "ROLE_ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAnyRoleUserConfiguredAndRoleIsUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasAnyRoleUserConfiguredAndRoleIsAdminThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(RoleUserConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("ADMIN")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/").with(user("user").roles("ADMIN"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleUserConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -332,37 +324,33 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasAnyRole("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRoleUserOrAdminConfiguredAndRoleIsUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserOrAdminConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRoleUserOrAdminConfiguredAndRoleIsAdminThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleUserOrAdminConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("ADMIN")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/").with(user("user").roles("ADMIN"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRoleUserOrAdminConfiguredAndRoleIsOtherThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(RoleUserOrAdminConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("OTHER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/").with(user("user").roles("OTHER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleUserOrAdminConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -371,34 +359,32 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasAnyRole("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasIpAddressConfiguredAndIpAddressMatchesThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(HasIpAddressConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(request -> {
|
||||
request.setRemoteAddr("192.168.1.0");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/").with(request -> {
|
||||
request.setRemoteAddr("192.168.1.0");
|
||||
return request;
|
||||
})).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHasIpAddressConfiguredAndIpAddressDoesNotMatchThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(HasIpAddressConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(request -> {
|
||||
request.setRemoteAddr("192.168.1.1");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/").with(request -> {
|
||||
request.setRemoteAddr("192.168.1.1");
|
||||
return request;
|
||||
})).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class HasIpAddressConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -409,27 +395,26 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().hasIpAddress("192.168.1.0");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAnonymousConfiguredAndAnonymousUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(AnonymousConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAnonymousConfiguredAndLoggedInUserThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(AnonymousConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/").with(user("user"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -440,27 +425,28 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().anonymous();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRememberMeConfiguredAndNoUserThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(RememberMeConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRememberMeConfiguredAndRememberMeTokenThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RememberMeConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(authentication(new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
this.mvc.perform(get("/").with(authentication(
|
||||
new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RememberMeConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -482,27 +468,26 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenDenyAllConfiguredAndNoUserThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(DenyAllConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWheDenyAllConfiguredAndUserLoggedInThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(DenyAllConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DenyAllConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -513,27 +498,28 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().denyAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenNotDenyAllConfiguredAndNoUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(NotDenyAllConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenNotDenyAllConfiguredAndRememberMeTokenThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(NotDenyAllConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(authentication(new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
this.mvc.perform(get("/").with(authentication(
|
||||
new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
.andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NotDenyAllConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -544,14 +530,15 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().not().denyAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenFullyAuthenticatedConfiguredAndRememberMeTokenThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(FullyAuthenticatedConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(authentication(new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
this.mvc.perform(get("/").with(authentication(
|
||||
new RememberMeAuthenticationToken("key", "user", AuthorityUtils.createAuthorityList("ROLE_USER")))))
|
||||
.andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@@ -559,13 +546,12 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
public void getWhenFullyAuthenticatedConfiguredAndUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(FullyAuthenticatedConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FullyAuthenticatedConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -578,37 +564,33 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().fullyAuthenticated();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenAccessRoleUserOrGetRequestConfiguredThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(AccessConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void postWhenAccessRoleUserOrGetRequestConfiguredAndRoleUserThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(AccessConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/")
|
||||
.with(csrf())
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(post("/").with(csrf()).with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void postWhenAccessRoleUserOrGetRequestConfiguredThenRespondsWithUnauthorized() throws Exception {
|
||||
this.spring.register(AccessConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/")
|
||||
.with(csrf()))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(post("/").with(csrf())).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AccessConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -621,19 +603,19 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.anyRequest().access("hasRole('ROLE_USER') or request.method == 'GET'");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authorizeRequestsWhenInvokedTwiceThenUsesOriginalConfiguration() throws Exception {
|
||||
this.spring.register(InvokeTwiceDoesNotResetConfig.class, BasicController.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/")
|
||||
.with(csrf()))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(post("/").with(csrf())).andExpect(status().isUnauthorized());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InvokeTwiceDoesNotResetConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -646,6 +628,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.authorizeRequests();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -655,6 +638,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AllPropertiesWorkConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
SecurityExpressionHandler<FilterInvocation> handler = new DefaultWebSecurityExpressionHandler();
|
||||
@@ -672,6 +656,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -686,6 +671,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthorizedRequestsWithPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ApplicationListener<AuthorizedEvent> AL = mock(ApplicationListener.class);
|
||||
|
||||
@Override
|
||||
@@ -708,46 +694,40 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
public ApplicationListener<AuthorizedEvent> applicationListener() {
|
||||
return AL;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenPermissionCheckAndRoleDoesNotMatchThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(UseBeansInExpressions.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/admin")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/admin").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenPermissionCheckAndRoleMatchesThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(UseBeansInExpressions.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/user")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/user").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenPermissionCheckAndAuthenticationNameMatchesThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(UseBeansInExpressions.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/allow")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/allow").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenPermissionCheckAndAuthenticationNameDoesNotMatchThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(UseBeansInExpressions.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/deny")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/deny").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class UseBeansInExpressions extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -766,40 +746,34 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
}
|
||||
|
||||
static class Checker {
|
||||
|
||||
public boolean check(Authentication authentication, String customArg) {
|
||||
return authentication.getName().contains(customArg);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCustomExpressionHandlerAndRoleDoesNotMatchThenRespondsWithForbidden()
|
||||
throws Exception {
|
||||
public void getWhenCustomExpressionHandlerAndRoleDoesNotMatchThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(CustomExpressionRootConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/admin")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/admin").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCustomExpressionHandlerAndRoleMatchesThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenCustomExpressionHandlerAndRoleMatchesThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CustomExpressionRootConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/user")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/user").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenCustomExpressionHandlerAndAuthenticationNameMatchesThenRespondsWithOk()
|
||||
throws Exception {
|
||||
public void getWhenCustomExpressionHandlerAndAuthenticationNameMatchesThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(CustomExpressionRootConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/allow")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/allow").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -807,13 +781,12 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(CustomExpressionRootConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/deny")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/deny").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomExpressionRootConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -835,14 +808,15 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
static class CustomExpressionHandler extends DefaultWebSecurityExpressionHandler {
|
||||
|
||||
@Override
|
||||
protected SecurityExpressionOperations createSecurityExpressionRoot(
|
||||
Authentication authentication, FilterInvocation fi) {
|
||||
protected SecurityExpressionOperations createSecurityExpressionRoot(Authentication authentication,
|
||||
FilterInvocation fi) {
|
||||
WebSecurityExpressionRoot root = new CustomExpressionRoot(authentication, fi);
|
||||
root.setPermissionEvaluator(getPermissionEvaluator());
|
||||
root.setTrustResolver(new AuthenticationTrustResolverImpl());
|
||||
root.setRoleHierarchy(getRoleHierarchy());
|
||||
return root;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class CustomExpressionRoot extends WebSecurityExpressionRoot {
|
||||
@@ -855,20 +829,22 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
Authentication auth = this.getAuthentication();
|
||||
return auth.getName().contains(customArg);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//SEC-3011
|
||||
// SEC-3011
|
||||
@Test
|
||||
public void configureWhenRegisteringObjectPostProcessorThenInvokedOnAccessDecisionManager() {
|
||||
this.spring.register(Sec3011Config.class).autowire();
|
||||
|
||||
verify(Sec3011Config.objectPostProcessor)
|
||||
.postProcess(any(AccessDecisionManager.class));
|
||||
verify(Sec3011Config.objectPostProcessor).postProcess(any(AccessDecisionManager.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class Sec3011Config extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
|
||||
@Override
|
||||
@@ -892,6 +868,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -899,8 +876,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(PermissionEvaluatorConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/allow"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/allow")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -908,8 +884,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(PermissionEvaluatorConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/deny"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/deny")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -917,8 +892,7 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(PermissionEvaluatorConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/allowObject"))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/allowObject")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -926,12 +900,12 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(PermissionEvaluatorConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/denyObject"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/denyObject")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PermissionEvaluatorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -949,7 +923,8 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
public PermissionEvaluator permissionEvaluator() {
|
||||
return new PermissionEvaluator() {
|
||||
@Override
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject, Object permission) {
|
||||
public boolean hasPermission(Authentication authentication, Object targetDomainObject,
|
||||
Object permission) {
|
||||
return "TESTOBJ".equals(targetDomainObject) && "PERMISSION".equals(permission);
|
||||
}
|
||||
|
||||
@@ -960,28 +935,26 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRegisteringRoleHierarchyAndRelatedRoleAllowedThenRespondsWithOk() throws Exception {
|
||||
this.spring.register(RoleHierarchyConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/allow")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isOk());
|
||||
this.mvc.perform(get("/allow").with(user("user").roles("USER"))).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenRegisteringRoleHierarchyAndNoRelatedRolesAllowedThenRespondsWithForbidden() throws Exception {
|
||||
this.spring.register(RoleHierarchyConfig.class, WildcardController.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/deny")
|
||||
.with(user("user").roles("USER")))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/deny").with(user("user").roles("USER"))).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RoleHierarchyConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -999,10 +972,12 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
roleHierarchy.setHierarchy("ROLE_USER > ROLE_MEMBER");
|
||||
return roleHierarchy;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class BasicController {
|
||||
|
||||
@GetMapping("/")
|
||||
public void rootGet() {
|
||||
}
|
||||
@@ -1010,19 +985,25 @@ public class ExpressionUrlAuthorizationConfigurerTests {
|
||||
@PostMapping("/")
|
||||
public void rootPost() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class WildcardController {
|
||||
|
||||
@GetMapping("/{path}")
|
||||
public void wildcard(@PathVariable String path) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -58,6 +58,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
* @since 5.1
|
||||
*/
|
||||
public class FormLoginConfigurerTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -66,19 +67,18 @@ public class FormLoginConfigurerTests {
|
||||
|
||||
@Test
|
||||
public void requestCache() throws Exception {
|
||||
this.spring.register(RequestCacheConfig.class,
|
||||
AuthenticationTestConfiguration.class).autowire();
|
||||
this.spring.register(RequestCacheConfig.class, AuthenticationTestConfiguration.class).autowire();
|
||||
|
||||
RequestCacheConfig config = this.spring.getContext().getBean(RequestCacheConfig.class);
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
|
||||
verify(config.requestCache).getRequest(any(), any());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestCacheConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
private RequestCache requestCache = mock(RequestCache.class);
|
||||
|
||||
@Override
|
||||
@@ -90,27 +90,28 @@ public class FormLoginConfigurerTests {
|
||||
.requestCache(this.requestCache);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestCacheAsBean() throws Exception {
|
||||
this.spring.register(RequestCacheBeanConfig.class,
|
||||
AuthenticationTestConfiguration.class).autowire();
|
||||
this.spring.register(RequestCacheBeanConfig.class, AuthenticationTestConfiguration.class).autowire();
|
||||
|
||||
RequestCache requestCache = this.spring.getContext().getBean(RequestCache.class);
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated());
|
||||
|
||||
verify(requestCache).getRequest(any(), any());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RequestCacheBeanConfig {
|
||||
|
||||
@Bean
|
||||
RequestCache requestCache() {
|
||||
return mock(RequestCache.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -118,16 +119,14 @@ public class FormLoginConfigurerTests {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("username", "user").password("password", "password"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenFormLoginConfiguredThenHasDefaultFailureUrl() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(formLogin().user("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?error"));
|
||||
}
|
||||
|
||||
@@ -135,38 +134,34 @@ public class FormLoginConfigurerTests {
|
||||
public void loginWhenFormLoginConfiguredThenHasDefaultSuccessUrl() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWhenFormLoginConfiguredThenNotSecured() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login"))
|
||||
.andExpect(status().isFound());
|
||||
this.mockMvc.perform(get("/login")).andExpect(status().isFound());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenFormLoginConfiguredThenSecured() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(post("/login"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mockMvc.perform(post("/login")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestProtectedWhenFormLoginConfiguredThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(FormLoginConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/private"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(get("/private")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("http://localhost/login"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
public void configure(WebSecurity web) {
|
||||
// @formatter:off
|
||||
@@ -196,6 +191,7 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -203,16 +199,14 @@ public class FormLoginConfigurerTests {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("username", "user").password("password", "password"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenFormLoginDefaultsInLambdaThenHasDefaultFailureUrl() throws Exception {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(formLogin().user("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?error"));
|
||||
}
|
||||
|
||||
@@ -220,38 +214,34 @@ public class FormLoginConfigurerTests {
|
||||
public void loginWhenFormLoginDefaultsInLambdaThenHasDefaultSuccessUrl() throws Exception {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWhenFormLoginDefaultsInLambdaThenNotSecured() throws Exception {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login"))
|
||||
.andExpect(status().isOk());
|
||||
this.mockMvc.perform(get("/login")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenFormLoginDefaultsInLambdaThenSecured() throws Exception {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(post("/login"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mockMvc.perform(post("/login")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestProtectedWhenFormLoginDefaultsInLambdaThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(FormLoginInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/private"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(get("/private")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("http://localhost/login"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -272,37 +262,34 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWhenFormLoginPermitAllThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginConfigPermitAll.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login"))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/login")).andExpect(status().isOk()).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWithErrorQueryWhenFormLoginPermitAllThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginConfigPermitAll.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login?error"))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/login?error")).andExpect(status().isOk()).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenFormLoginPermitAllAndInvalidUserThenRedirectsToLoginPageWithError() throws Exception {
|
||||
this.spring.register(FormLoginConfigPermitAll.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(formLogin().user("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?error"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginConfigPermitAll extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -314,30 +301,28 @@ public class FormLoginConfigurerTests {
|
||||
.permitAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWhenCustomLoginPageThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authenticate"))
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/authenticate")).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWithErrorQueryWhenCustomLoginPageThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authenticate?error"))
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/authenticate?error")).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenCustomLoginPageAndInvalidUserThenRedirectsToCustomLoginPageWithError() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin("/authenticate").user("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(formLogin("/authenticate").user("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/authenticate?error"));
|
||||
}
|
||||
|
||||
@@ -345,20 +330,19 @@ public class FormLoginConfigurerTests {
|
||||
public void logoutWhenCustomLoginPageThenRedirectsToCustomLoginPage() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(logout())
|
||||
.andExpect(redirectedUrl("/authenticate?logout"));
|
||||
this.mockMvc.perform(logout()).andExpect(redirectedUrl("/authenticate?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWithLogoutQueryWhenCustomLoginPageThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authenticate?logout"))
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/authenticate?logout")).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginDefaultsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -374,18 +358,19 @@ public class FormLoginConfigurerTests {
|
||||
.permitAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getLoginPageWhenCustomLoginPageInLambdaThenPermittedAndNoRedirect() throws Exception {
|
||||
this.spring.register(FormLoginDefaultsInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/authenticate"))
|
||||
.andExpect(redirectedUrl(null));
|
||||
this.mockMvc.perform(get("/authenticate")).andExpect(redirectedUrl(null));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginDefaultsInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -402,19 +387,19 @@ public class FormLoginConfigurerTests {
|
||||
.logout(LogoutConfigurer::permitAll);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenCustomLoginProcessingUrlThenRedirectsToHome() throws Exception {
|
||||
this.spring.register(FormLoginLoginProcessingUrlConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin("/loginCheck"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
this.mockMvc.perform(formLogin("/loginCheck")).andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginLoginProcessingUrlConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -445,19 +430,19 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenCustomLoginProcessingUrlInLambdaThenRedirectsToHome() throws Exception {
|
||||
this.spring.register(FormLoginLoginProcessingUrlInLambdaConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin("/loginCheck"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"));
|
||||
this.mockMvc.perform(formLogin("/loginCheck")).andExpect(status().isFound()).andExpect(redirectedUrl("/"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginLoginProcessingUrlInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -490,6 +475,7 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -498,8 +484,7 @@ public class FormLoginConfigurerTests {
|
||||
when(FormLoginUsesPortMapperConfig.PORT_MAPPER.lookupHttpsPort(any())).thenReturn(9443);
|
||||
this.spring.register(FormLoginUsesPortMapperConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("http://localhost:9090"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(get("http://localhost:9090")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("https://localhost:9443/login"));
|
||||
|
||||
verify(FormLoginUsesPortMapperConfig.PORT_MAPPER).lookupHttpsPort(any());
|
||||
@@ -507,6 +492,7 @@ public class FormLoginConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class FormLoginUsesPortMapperConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static PortMapper PORT_MAPPER;
|
||||
|
||||
@Override
|
||||
@@ -522,23 +508,24 @@ public class FormLoginConfigurerTests {
|
||||
.portMapper()
|
||||
.portMapper(PORT_MAPPER);
|
||||
// @formatter:on
|
||||
LoginUrlAuthenticationEntryPoint authenticationEntryPoint =
|
||||
(LoginUrlAuthenticationEntryPoint) http.getConfigurer(FormLoginConfigurer.class).getAuthenticationEntryPoint();
|
||||
LoginUrlAuthenticationEntryPoint authenticationEntryPoint = (LoginUrlAuthenticationEntryPoint) http
|
||||
.getConfigurer(FormLoginConfigurer.class).getAuthenticationEntryPoint();
|
||||
authenticationEntryPoint.setForceHttps(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void failureUrlWhenPermitAllAndFailureHandlerThenSecured() throws Exception {
|
||||
this.spring.register(PermitAllIgnoresFailureHandlerConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(get("/login?error"))
|
||||
.andExpect(status().isFound())
|
||||
this.mockMvc.perform(get("/login?error")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("http://localhost/login"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class PermitAllIgnoresFailureHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationFailureHandler FAILURE_HANDLER = mock(AuthenticationFailureHandler.class);
|
||||
|
||||
@Override
|
||||
@@ -553,18 +540,19 @@ public class FormLoginConfigurerTests {
|
||||
.permitAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void formLoginWhenInvokedTwiceThenUsesOriginalUsernameParameter() throws Exception {
|
||||
this.spring.register(DuplicateInvocationsDoesNotOverrideConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("custom-username", "user"))
|
||||
.andExpect(authenticated());
|
||||
this.mockMvc.perform(formLogin().user("custom-username", "user")).andExpect(authenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DuplicateInvocationsDoesNotOverrideConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -584,22 +572,21 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenInvalidLoginAndFailureForwardUrlThenForwardsToFailureForwardUrl() throws Exception {
|
||||
this.spring.register(FormLoginUserForwardAuthenticationSuccessAndFailureConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin().user("invalid"))
|
||||
.andExpect(forwardedUrl("/failure_forward_url"));
|
||||
this.mockMvc.perform(formLogin().user("invalid")).andExpect(forwardedUrl("/failure_forward_url"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void loginWhenSuccessForwardUrlThenForwardsToSuccessForwardUrl() throws Exception {
|
||||
this.spring.register(FormLoginUserForwardAuthenticationSuccessAndFailureConfig.class).autowire();
|
||||
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(forwardedUrl("/success_forward_url"));
|
||||
this.mockMvc.perform(formLogin()).andExpect(forwardedUrl("/success_forward_url"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -629,6 +616,7 @@ public class FormLoginConfigurerTests {
|
||||
.withUser(PasswordEncodedUser.user());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -645,8 +633,7 @@ public class FormLoginConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(LoginUrlAuthenticationEntryPoint.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(LoginUrlAuthenticationEntryPoint.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -654,12 +641,12 @@ public class FormLoginConfigurerTests {
|
||||
ObjectPostProcessorConfig.objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(ExceptionTranslationFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(ExceptionTranslationFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor;
|
||||
|
||||
@Override
|
||||
@@ -676,12 +663,16 @@ public class FormLoginConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -46,33 +46,32 @@ public class HeadersConfigurerEagerHeadersTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
public static class HeadersAtTheBeginningOfRequestConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
//@ formatter:off
|
||||
http
|
||||
.headers()
|
||||
.addObjectPostProcessor(new ObjectPostProcessor<HeaderWriterFilter>() {
|
||||
@Override
|
||||
public HeaderWriterFilter postProcess(HeaderWriterFilter filter) {
|
||||
filter.setShouldWriteHeadersEagerly(true);
|
||||
return filter;
|
||||
}
|
||||
});
|
||||
//@ formatter:on
|
||||
// @ formatter:off
|
||||
http.headers().addObjectPostProcessor(new ObjectPostProcessor<HeaderWriterFilter>() {
|
||||
@Override
|
||||
public HeaderWriterFilter postProcess(HeaderWriterFilter filter) {
|
||||
filter.setShouldWriteHeadersEagerly(true);
|
||||
return filter;
|
||||
}
|
||||
});
|
||||
// @ formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenHeadersEagerlyConfiguredThenHeadersAreWritten() throws Exception {
|
||||
this.spring.register(HeadersAtTheBeginningOfRequestConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("X-Content-Type-Options", "nosniff"))
|
||||
this.mvc.perform(get("/").secure(true)).andExpect(header().string("X-Content-Type-Options", "nosniff"))
|
||||
.andExpect(header().string("X-Frame-Options", "DENY"))
|
||||
.andExpect(header().string("Strict-Transport-Security", "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string(CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(EXPIRES, "0"))
|
||||
.andExpect(header().string(PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(EXPIRES, "0")).andExpect(header().string(PRAGMA, "no-cache"))
|
||||
.andExpect(header().string("X-XSS-Protection", "1; mode=block"));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -65,12 +65,12 @@ public class HeadersConfigurerTests {
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff"))
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS, XFrameOptionsMode.DENY.name()))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(
|
||||
header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactlyInAnyOrder(
|
||||
HttpHeaders.X_CONTENT_TYPE_OPTIONS, HttpHeaders.X_FRAME_OPTIONS, HttpHeaders.STRICT_TRANSPORT_SECURITY,
|
||||
HttpHeaders.CACHE_CONTROL, HttpHeaders.EXPIRES, HttpHeaders.PRAGMA, HttpHeaders.X_XSS_PROTECTION);
|
||||
@@ -86,6 +86,7 @@ public class HeadersConfigurerTests {
|
||||
.headers();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -95,12 +96,12 @@ public class HeadersConfigurerTests {
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff"))
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS, XFrameOptionsMode.DENY.name()))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(
|
||||
header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactlyInAnyOrder(
|
||||
HttpHeaders.X_CONTENT_TYPE_OPTIONS, HttpHeaders.X_FRAME_OPTIONS, HttpHeaders.STRICT_TRANSPORT_SECURITY,
|
||||
HttpHeaders.CACHE_CONTROL, HttpHeaders.EXPIRES, HttpHeaders.PRAGMA, HttpHeaders.X_XSS_PROTECTION);
|
||||
@@ -116,6 +117,7 @@ public class HeadersConfigurerTests {
|
||||
.headers(withDefaults());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -124,8 +126,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ContentTypeOptionsConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.X_CONTENT_TYPE_OPTIONS);
|
||||
}
|
||||
|
||||
@@ -141,16 +142,15 @@ public class HeadersConfigurerTests {
|
||||
.contentTypeOptions();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenOnlyContentTypeConfiguredInLambdaThenOnlyContentTypeHeaderInResponse()
|
||||
throws Exception {
|
||||
public void getWhenOnlyContentTypeConfiguredInLambdaThenOnlyContentTypeHeaderInResponse() throws Exception {
|
||||
this.spring.register(ContentTypeOptionsInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_CONTENT_TYPE_OPTIONS, "nosniff")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.X_CONTENT_TYPE_OPTIONS);
|
||||
}
|
||||
|
||||
@@ -168,6 +168,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -176,8 +177,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(FrameOptionsConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS, XFrameOptionsMode.DENY.name()))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_FRAME_OPTIONS, XFrameOptionsMode.DENY.name())).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.X_FRAME_OPTIONS);
|
||||
}
|
||||
|
||||
@@ -193,6 +193,7 @@ public class HeadersConfigurerTests {
|
||||
.frameOptions();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -201,7 +202,8 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(HstsConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andExpect(
|
||||
header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.STRICT_TRANSPORT_SECURITY);
|
||||
}
|
||||
@@ -218,6 +220,7 @@ public class HeadersConfigurerTests {
|
||||
.httpStrictTransportSecurity();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -228,8 +231,7 @@ public class HeadersConfigurerTests {
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactlyInAnyOrder(HttpHeaders.CACHE_CONTROL,
|
||||
HttpHeaders.EXPIRES, HttpHeaders.PRAGMA);
|
||||
}
|
||||
@@ -246,6 +248,7 @@ public class HeadersConfigurerTests {
|
||||
.cacheControl();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -256,8 +259,7 @@ public class HeadersConfigurerTests {
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate"))
|
||||
.andExpect(header().string(HttpHeaders.EXPIRES, "0"))
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.PRAGMA, "no-cache")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactlyInAnyOrder(HttpHeaders.CACHE_CONTROL,
|
||||
HttpHeaders.EXPIRES, HttpHeaders.PRAGMA);
|
||||
}
|
||||
@@ -276,6 +278,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -284,8 +287,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(XssProtectionConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.X_XSS_PROTECTION);
|
||||
}
|
||||
|
||||
@@ -301,16 +303,15 @@ public class HeadersConfigurerTests {
|
||||
.xssProtection();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenOnlyXssProtectionConfiguredInLambdaThenOnlyXssProtectionHeaderInResponse()
|
||||
throws Exception {
|
||||
public void getWhenOnlyXssProtectionConfiguredInLambdaThenOnlyXssProtectionHeaderInResponse() throws Exception {
|
||||
this.spring.register(XssProtectionInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.X_XSS_PROTECTION, "1; mode=block")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.X_XSS_PROTECTION);
|
||||
}
|
||||
|
||||
@@ -328,6 +329,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -350,6 +352,7 @@ public class HeadersConfigurerTests {
|
||||
.frameOptions().sameOrigin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -375,14 +378,14 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHeaderDefaultsDisabledAndPublicHpkpWithNoPinThenNoHeadersInResponse() throws Exception {
|
||||
this.spring.register(HpkpConfigNoPins.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andReturn();
|
||||
MvcResult mvcResult = this.mvc.perform(get("/")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).isEmpty();
|
||||
}
|
||||
|
||||
@@ -398,11 +401,11 @@ public class HeadersConfigurerTests {
|
||||
.httpPublicKeyPinning();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenSecureRequestAndHpkpWithPinThenPublicKeyPinsReportOnlyHeaderInResponse()
|
||||
throws Exception {
|
||||
public void getWhenSecureRequestAndHpkpWithPinThenPublicKeyPinsReportOnlyHeaderInResponse() throws Exception {
|
||||
this.spring.register(HpkpConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
@@ -413,12 +416,10 @@ public class HeadersConfigurerTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenInsecureRequestHeaderDefaultsDisabledAndHpkpWithPinThenNoHeadersInResponse()
|
||||
throws Exception {
|
||||
public void getWhenInsecureRequestHeaderDefaultsDisabledAndHpkpWithPinThenNoHeadersInResponse() throws Exception {
|
||||
this.spring.register(HpkpConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/"))
|
||||
.andReturn();
|
||||
MvcResult mvcResult = this.mvc.perform(get("/")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).isEmpty();
|
||||
}
|
||||
|
||||
@@ -435,6 +436,7 @@ public class HeadersConfigurerTests {
|
||||
.addSha256Pins("d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -442,9 +444,9 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HpkpConfigWithPins.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; pin-sha256=\"E9CZ9INDbd+2eRQozYqqbQ2yXLVKB9+xcprMF+44U1g=\""))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header().string(
|
||||
HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; pin-sha256=\"E9CZ9INDbd+2eRQozYqqbQ2yXLVKB9+xcprMF+44U1g=\""))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY);
|
||||
}
|
||||
@@ -466,6 +468,7 @@ public class HeadersConfigurerTests {
|
||||
.withPins(pins);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -493,6 +496,7 @@ public class HeadersConfigurerTests {
|
||||
.maxAgeInSeconds(604800);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -520,6 +524,7 @@ public class HeadersConfigurerTests {
|
||||
.reportOnly(false);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -527,9 +532,9 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HpkpConfigIncludeSubDomains.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; includeSubDomains"))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header().string(
|
||||
HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; includeSubDomains"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY);
|
||||
}
|
||||
@@ -548,15 +553,16 @@ public class HeadersConfigurerTests {
|
||||
.includeSubDomains(true);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenHpkpWithReportUriThenPublicKeyPinsReportOnlyHeaderWithReportUriInResponse() throws Exception {
|
||||
this.spring.register(HpkpConfigWithReportURI.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header().string(
|
||||
HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY);
|
||||
}
|
||||
@@ -575,6 +581,7 @@ public class HeadersConfigurerTests {
|
||||
.reportUri(new URI("https://example.net/pkp-report"));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -582,9 +589,9 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HpkpConfigWithReportURIAsString.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header().string(
|
||||
HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY);
|
||||
}
|
||||
@@ -603,6 +610,7 @@ public class HeadersConfigurerTests {
|
||||
.reportUri("https://example.net/pkp-report");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -610,9 +618,9 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HpkpWithReportUriInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header().string(
|
||||
HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY,
|
||||
"max-age=5184000 ; pin-sha256=\"d6qzRu9zOECb90Uez27xWltNsj0e1Md7GkYYkVoZWmM=\" ; report-uri=\"https://example.net/pkp-report\""))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.PUBLIC_KEY_PINS_REPORT_ONLY);
|
||||
}
|
||||
@@ -635,6 +643,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -642,8 +651,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ContentSecurityPolicyDefaultConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY, "default-src 'self'"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY, "default-src 'self'")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY);
|
||||
}
|
||||
|
||||
@@ -659,17 +667,20 @@ public class HeadersConfigurerTests {
|
||||
.contentSecurityPolicy("default-src 'self'");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getWhenContentSecurityPolicyWithReportOnlyThenContentSecurityPolicyReportOnlyHeaderInResponse() throws Exception {
|
||||
public void getWhenContentSecurityPolicyWithReportOnlyThenContentSecurityPolicyReportOnlyHeaderInResponse()
|
||||
throws Exception {
|
||||
this.spring.register(ContentSecurityPolicyReportOnlyConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY,
|
||||
"default-src 'self'; script-src trustedscripts.example.com"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY);
|
||||
assertThat(mvcResult.getResponse().getHeaderNames())
|
||||
.containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -685,6 +696,7 @@ public class HeadersConfigurerTests {
|
||||
.reportOnly();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -696,7 +708,8 @@ public class HeadersConfigurerTests {
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY,
|
||||
"default-src 'self'; script-src trustedscripts.example.com"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY);
|
||||
assertThat(mvcResult.getResponse().getHeaderNames())
|
||||
.containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY_REPORT_ONLY);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -717,13 +730,13 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenContentSecurityPolicyEmptyThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(ContentSecurityPolicyInvalidConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -738,13 +751,13 @@ public class HeadersConfigurerTests {
|
||||
.contentSecurityPolicy("");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenContentSecurityPolicyEmptyInLambdaThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(ContentSecurityPolicyInvalidInLambdaConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -763,6 +776,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -770,9 +784,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ContentSecurityPolicyNoDirectivesInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY,
|
||||
"default-src 'self'"))
|
||||
.andReturn();
|
||||
.andExpect(header().string(HttpHeaders.CONTENT_SECURITY_POLICY, "default-src 'self'")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.CONTENT_SECURITY_POLICY);
|
||||
}
|
||||
|
||||
@@ -790,6 +802,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -797,8 +810,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ReferrerPolicyDefaultConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.NO_REFERRER.getPolicy()))
|
||||
.andReturn();
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.NO_REFERRER.getPolicy())).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly("Referrer-Policy");
|
||||
}
|
||||
|
||||
@@ -814,6 +826,7 @@ public class HeadersConfigurerTests {
|
||||
.referrerPolicy();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -821,8 +834,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ReferrerPolicyDefaultInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.NO_REFERRER.getPolicy()))
|
||||
.andReturn();
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.NO_REFERRER.getPolicy())).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly("Referrer-Policy");
|
||||
}
|
||||
|
||||
@@ -840,6 +852,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -848,8 +861,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ReferrerPolicyCustomConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.SAME_ORIGIN.getPolicy()))
|
||||
.andReturn();
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.SAME_ORIGIN.getPolicy())).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly("Referrer-Policy");
|
||||
}
|
||||
|
||||
@@ -865,6 +877,7 @@ public class HeadersConfigurerTests {
|
||||
.referrerPolicy(ReferrerPolicy.SAME_ORIGIN);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -872,8 +885,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(ReferrerPolicyCustomInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.SAME_ORIGIN.getPolicy()))
|
||||
.andReturn();
|
||||
.andExpect(header().string("Referrer-Policy", ReferrerPolicy.SAME_ORIGIN.getPolicy())).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly("Referrer-Policy");
|
||||
}
|
||||
|
||||
@@ -893,6 +905,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -900,8 +913,7 @@ public class HeadersConfigurerTests {
|
||||
this.spring.register(FeaturePolicyConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string("Feature-Policy", "geolocation 'self'"))
|
||||
.andReturn();
|
||||
.andExpect(header().string("Feature-Policy", "geolocation 'self'")).andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly("Feature-Policy");
|
||||
}
|
||||
|
||||
@@ -917,13 +929,13 @@ public class HeadersConfigurerTests {
|
||||
.featurePolicy("geolocation 'self'");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenFeaturePolicyEmptyThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(FeaturePolicyInvalidConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -938,6 +950,7 @@ public class HeadersConfigurerTests {
|
||||
.featurePolicy("");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -945,9 +958,8 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HstsWithPreloadConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY,
|
||||
"max-age=31536000 ; includeSubDomains ; preload"))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header()
|
||||
.string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains ; preload"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.STRICT_TRANSPORT_SECURITY);
|
||||
}
|
||||
@@ -965,6 +977,7 @@ public class HeadersConfigurerTests {
|
||||
.preload(true);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -972,9 +985,8 @@ public class HeadersConfigurerTests {
|
||||
throws Exception {
|
||||
this.spring.register(HstsWithPreloadInLambdaConfig.class).autowire();
|
||||
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true))
|
||||
.andExpect(header().string(HttpHeaders.STRICT_TRANSPORT_SECURITY,
|
||||
"max-age=31536000 ; includeSubDomains ; preload"))
|
||||
MvcResult mvcResult = this.mvc.perform(get("/").secure(true)).andExpect(header()
|
||||
.string(HttpHeaders.STRICT_TRANSPORT_SECURITY, "max-age=31536000 ; includeSubDomains ; preload"))
|
||||
.andReturn();
|
||||
assertThat(mvcResult.getResponse().getHeaderNames()).containsExactly(HttpHeaders.STRICT_TRANSPORT_SECURITY);
|
||||
}
|
||||
@@ -993,5 +1005,7 @@ public class HeadersConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -62,12 +62,12 @@ public class HttpBasicConfigurerTests {
|
||||
public void configureWhenRegisteringObjectPostProcessorThenInvokedOnBasicAuthenticationFilter() {
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(BasicAuthenticationFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(BasicAuthenticationFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
|
||||
@Override
|
||||
@@ -82,26 +82,29 @@ public class HttpBasicConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void httpBasicWhenUsingDefaultsInLambdaThenResponseIncludesBasicChallenge() throws Exception {
|
||||
this.spring.register(DefaultsLambdaEntryPointConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string("WWW-Authenticate", "Basic realm=\"Realm\""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultsLambdaEntryPointConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -121,20 +124,21 @@ public class HttpBasicConfigurerTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//SEC-2198
|
||||
// SEC-2198
|
||||
@Test
|
||||
public void httpBasicWhenUsingDefaultsThenResponseIncludesBasicChallenge() throws Exception {
|
||||
this.spring.register(DefaultsEntryPointConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string("WWW-Authenticate", "Basic realm=\"Realm\""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DefaultsEntryPointConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -153,6 +157,7 @@ public class HttpBasicConfigurerTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -161,14 +166,13 @@ public class HttpBasicConfigurerTests {
|
||||
|
||||
this.mvc.perform(get("/"));
|
||||
|
||||
verify(CustomAuthenticationEntryPointConfig.ENTRY_POINT)
|
||||
.commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class),
|
||||
any(AuthenticationException.class));
|
||||
verify(CustomAuthenticationEntryPointConfig.ENTRY_POINT).commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class), any(AuthenticationException.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomAuthenticationEntryPointConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationEntryPoint ENTRY_POINT = mock(AuthenticationEntryPoint.class);
|
||||
|
||||
@Override
|
||||
@@ -190,6 +194,7 @@ public class HttpBasicConfigurerTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -198,14 +203,13 @@ public class HttpBasicConfigurerTests {
|
||||
|
||||
this.mvc.perform(get("/"));
|
||||
|
||||
verify(DuplicateDoesNotOverrideConfig.ENTRY_POINT)
|
||||
.commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class),
|
||||
any(AuthenticationException.class));
|
||||
verify(DuplicateDoesNotOverrideConfig.ENTRY_POINT).commence(any(HttpServletRequest.class),
|
||||
any(HttpServletResponse.class), any(AuthenticationException.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DuplicateDoesNotOverrideConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static AuthenticationEntryPoint ENTRY_POINT = mock(AuthenticationEntryPoint.class);
|
||||
|
||||
@Override
|
||||
@@ -229,16 +233,15 @@ public class HttpBasicConfigurerTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//SEC-3019
|
||||
// SEC-3019
|
||||
@Test
|
||||
public void httpBasicWhenRememberMeConfiguredThenSetsRememberMeCookie() throws Exception {
|
||||
this.spring.register(BasicUsesRememberMeConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password"))
|
||||
.param("remember-me", "true"))
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password")).param("remember-me", "true"))
|
||||
.andExpect(cookie().exists("remember-me"));
|
||||
}
|
||||
|
||||
@@ -259,7 +262,7 @@ public class HttpBasicConfigurerTests {
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
return new InMemoryUserDetailsManager(
|
||||
// @formatter:off
|
||||
// @formatter:off
|
||||
User.withDefaultPasswordEncoder()
|
||||
.username("user")
|
||||
.password("password")
|
||||
@@ -268,5 +271,7 @@ public class HttpBasicConfigurerTests {
|
||||
// @formatter:on
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -40,10 +40,13 @@ import org.springframework.web.context.support.AnnotationConfigWebApplicationCon
|
||||
*
|
||||
*/
|
||||
public class HttpSecurityAntMatchersTests {
|
||||
|
||||
AnnotationConfigWebApplicationContext context;
|
||||
|
||||
MockHttpServletRequest request;
|
||||
|
||||
MockHttpServletResponse response;
|
||||
|
||||
MockFilterChain chain;
|
||||
|
||||
@Autowired
|
||||
@@ -77,6 +80,7 @@ public class HttpSecurityAntMatchersTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntMatchersNoPatternsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -95,6 +99,7 @@ public class HttpSecurityAntMatchersTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-3135
|
||||
@@ -111,6 +116,7 @@ public class HttpSecurityAntMatchersTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class AntMatchersEmptyPatternsConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -130,6 +136,7 @@ public class HttpSecurityAntMatchersTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void loadConfig(Class<?>... configs) {
|
||||
@@ -140,5 +147,4 @@ public class HttpSecurityAntMatchersTests {
|
||||
context.getAutowireCapableBeanFactory().autowireBean(this);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -41,10 +41,13 @@ import org.springframework.web.context.support.AnnotationConfigWebApplicationCon
|
||||
*
|
||||
*/
|
||||
public class HttpSecurityLogoutTests {
|
||||
|
||||
AnnotationConfigWebApplicationContext context;
|
||||
|
||||
MockHttpServletRequest request;
|
||||
|
||||
MockHttpServletResponse response;
|
||||
|
||||
MockFilterChain chain;
|
||||
|
||||
@Autowired
|
||||
@@ -72,7 +75,8 @@ public class HttpSecurityLogoutTests {
|
||||
SecurityContext currentContext = SecurityContextHolder.createEmptyContext();
|
||||
currentContext.setAuthentication(new TestingAuthenticationToken("user", "password", "ROLE_USER"));
|
||||
|
||||
request.getSession().setAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY, currentContext);
|
||||
request.getSession().setAttribute(HttpSessionSecurityContextRepository.SPRING_SECURITY_CONTEXT_KEY,
|
||||
currentContext);
|
||||
request.setMethod("POST");
|
||||
request.setServletPath("/logout");
|
||||
|
||||
@@ -84,6 +88,7 @@ public class HttpSecurityLogoutTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
static class ClearAuthenticationFalseConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -100,6 +105,7 @@ public class HttpSecurityLogoutTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void loadConfig(Class<?>... configs) {
|
||||
@@ -110,5 +116,4 @@ public class HttpSecurityLogoutTests {
|
||||
context.getAutowireCapableBeanFactory().autowireBean(this);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -47,10 +47,13 @@ import static org.springframework.security.config.Customizer.withDefaults;
|
||||
*
|
||||
*/
|
||||
public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
AnnotationConfigWebApplicationContext context;
|
||||
|
||||
MockHttpServletRequest request;
|
||||
|
||||
MockHttpServletResponse response;
|
||||
|
||||
MockFilterChain chain;
|
||||
|
||||
@Autowired
|
||||
@@ -78,24 +81,21 @@ public class HttpSecurityRequestMatchersTests {
|
||||
this.request.setServletPath("/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -109,6 +109,7 @@ public class HttpSecurityRequestMatchersTests {
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class MvcMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -130,11 +131,14 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -144,30 +148,28 @@ public class HttpSecurityRequestMatchersTests {
|
||||
this.request.setServletPath("/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class RequestMatchersMvcMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -191,11 +193,14 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -205,30 +210,28 @@ public class HttpSecurityRequestMatchersTests {
|
||||
this.request.setServletPath("/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path.html");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
this.request.setServletPath("/path/");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class RequestMatchersMvcMatcherInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -247,11 +250,14 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -262,8 +268,7 @@ public class HttpSecurityRequestMatchersTests {
|
||||
this.request.setRequestURI("/spring/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -286,8 +291,8 @@ public class HttpSecurityRequestMatchersTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class RequestMatchersMvcMatcherServeltPathConfig
|
||||
extends WebSecurityConfigurerAdapter {
|
||||
static class RequestMatchersMvcMatcherServeltPathConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -312,11 +317,14 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -327,8 +335,7 @@ public class HttpSecurityRequestMatchersTests {
|
||||
this.request.setRequestURI("/spring/path");
|
||||
this.springSecurityFilterChain.doFilter(this.request, this.response, this.chain);
|
||||
|
||||
assertThat(this.response.getStatus())
|
||||
.isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
assertThat(this.response.getStatus()).isEqualTo(HttpServletResponse.SC_UNAUTHORIZED);
|
||||
|
||||
setup();
|
||||
|
||||
@@ -351,8 +358,8 @@ public class HttpSecurityRequestMatchersTests {
|
||||
@EnableWebSecurity
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
static class RequestMatchersMvcMatcherServletPathInLambdaConfig
|
||||
extends WebSecurityConfigurerAdapter {
|
||||
static class RequestMatchersMvcMatcherServletPathInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -372,19 +379,24 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class PathController {
|
||||
|
||||
@RequestMapping("/path")
|
||||
public String path() {
|
||||
return "path";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class LegacyMvcMatchingConfig implements WebMvcConfigurer {
|
||||
|
||||
@Override
|
||||
public void configurePathMatch(PathMatchConfigurer configurer) {
|
||||
configurer.setUseSuffixPatternMatch(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void loadConfig(Class<?>... configs) {
|
||||
@@ -395,4 +407,5 @@ public class HttpSecurityRequestMatchersTests {
|
||||
|
||||
this.context.getAutowireCapableBeanFactory().autowireBean(this);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -59,9 +59,9 @@ public class Issue55Tests {
|
||||
assertThat(filter.getAuthenticationManager().authenticate(token)).isEqualTo(CustomAuthenticationManager.RESULT);
|
||||
}
|
||||
|
||||
|
||||
@EnableWebSecurity
|
||||
static class WebSecurityConfigurerAdapterDefaultsAuthManagerConfig {
|
||||
|
||||
@Component
|
||||
public static class WebSecurityAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@@ -73,19 +73,24 @@ public class Issue55Tests {
|
||||
.anyRequest().hasRole("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
public static class AuthenticationManagerConfiguration {
|
||||
|
||||
@Bean
|
||||
public AuthenticationManager authenticationManager() throws Exception {
|
||||
return new CustomAuthenticationManager();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void multiHttpWebSecurityConfigurerAdapterDefaultsToAutowired() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
|
||||
public void multiHttpWebSecurityConfigurerAdapterDefaultsToAutowired()
|
||||
throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
|
||||
TestingAuthenticationToken token = new TestingAuthenticationToken("test", "this");
|
||||
this.spring.register(MultiWebSecurityConfigurerAdapterDefaultsAuthManagerConfig.class);
|
||||
this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
@@ -93,15 +98,19 @@ public class Issue55Tests {
|
||||
FilterSecurityInterceptor filter = (FilterSecurityInterceptor) findFilter(FilterSecurityInterceptor.class, 0);
|
||||
assertThat(filter.getAuthenticationManager().authenticate(token)).isEqualTo(CustomAuthenticationManager.RESULT);
|
||||
|
||||
FilterSecurityInterceptor secondFilter = (FilterSecurityInterceptor) findFilter(FilterSecurityInterceptor.class, 1);
|
||||
assertThat(secondFilter.getAuthenticationManager().authenticate(token)).isEqualTo(CustomAuthenticationManager.RESULT);
|
||||
FilterSecurityInterceptor secondFilter = (FilterSecurityInterceptor) findFilter(FilterSecurityInterceptor.class,
|
||||
1);
|
||||
assertThat(secondFilter.getAuthenticationManager().authenticate(token))
|
||||
.isEqualTo(CustomAuthenticationManager.RESULT);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class MultiWebSecurityConfigurerAdapterDefaultsAuthManagerConfig {
|
||||
|
||||
@Component
|
||||
@Order(1)
|
||||
public static class ApiWebSecurityAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -110,10 +119,12 @@ public class Issue55Tests {
|
||||
.anyRequest().hasRole("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Component
|
||||
public static class WebSecurityAdapter extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -122,23 +133,29 @@ public class Issue55Tests {
|
||||
.anyRequest().hasRole("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
public static class AuthenticationManagerConfiguration {
|
||||
|
||||
@Bean
|
||||
public AuthenticationManager authenticationManager() throws Exception {
|
||||
return new CustomAuthenticationManager();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class CustomAuthenticationManager implements AuthenticationManager {
|
||||
|
||||
static Authentication RESULT = new TestingAuthenticationToken("test", "this", "ROLE_USER");
|
||||
|
||||
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
|
||||
return RESULT;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Filter findFilter(Class<?> filter, int index) {
|
||||
@@ -154,4 +171,5 @@ public class Issue55Tests {
|
||||
SecurityFilterChain filterChain(int index) {
|
||||
return this.spring.getContext().getBean(FilterChainProxy.class).getFilterChains().get(index);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -76,6 +76,7 @@ public class JeeConfigurerTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor;
|
||||
|
||||
@Override
|
||||
@@ -90,13 +91,16 @@ public class JeeConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -105,18 +109,16 @@ public class JeeConfigurerTests {
|
||||
Principal user = mock(Principal.class);
|
||||
when(user.getName()).thenReturn("user");
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.principal(user)
|
||||
.with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(authenticated().withRoles("USER"));
|
||||
this.mvc.perform(get("/").principal(user).with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
})).andExpect(authenticated().withRoles("USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class InvokeTwiceDoesNotOverride extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -127,6 +129,7 @@ public class JeeConfigurerTests {
|
||||
.jee();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -135,18 +138,16 @@ public class JeeConfigurerTests {
|
||||
Principal user = mock(Principal.class);
|
||||
when(user.getName()).thenReturn("user");
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.principal(user)
|
||||
.with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(authenticated().withRoles("USER"));
|
||||
this.mvc.perform(get("/").principal(user).with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
})).andExpect(authenticated().withRoles("USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
public static class JeeMappableRolesConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -161,6 +162,7 @@ public class JeeConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -169,14 +171,11 @@ public class JeeConfigurerTests {
|
||||
Principal user = mock(Principal.class);
|
||||
when(user.getName()).thenReturn("user");
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.principal(user)
|
||||
.with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(authenticated().withAuthorities(AuthorityUtils.createAuthorityList("ROLE_USER")));
|
||||
this.mvc.perform(get("/").principal(user).with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
})).andExpect(authenticated().withAuthorities(AuthorityUtils.createAuthorityList("ROLE_USER")));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -196,6 +195,7 @@ public class JeeConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -209,20 +209,18 @@ public class JeeConfigurerTests {
|
||||
when(JeeCustomAuthenticatedUserDetailsServiceConfig.authenticationUserDetailsService.loadUserDetails(any()))
|
||||
.thenReturn(userDetails);
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.principal(user)
|
||||
.with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
}))
|
||||
.andExpect(authenticated().withRoles("USER"));
|
||||
this.mvc.perform(get("/").principal(user).with(request -> {
|
||||
request.addUserRole("ROLE_ADMIN");
|
||||
request.addUserRole("ROLE_USER");
|
||||
return request;
|
||||
})).andExpect(authenticated().withRoles("USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
public static class JeeCustomAuthenticatedUserDetailsServiceConfig extends WebSecurityConfigurerAdapter {
|
||||
static AuthenticationUserDetailsService authenticationUserDetailsService =
|
||||
mock(AuthenticationUserDetailsService.class);
|
||||
|
||||
static AuthenticationUserDetailsService authenticationUserDetailsService = mock(
|
||||
AuthenticationUserDetailsService.class);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -238,5 +236,7 @@ public class JeeConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -43,8 +43,8 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
|
||||
/**
|
||||
*
|
||||
* Tests for {@link HeaderWriterLogoutHandler} that passing {@link ClearSiteDataHeaderWriter}
|
||||
* implementation.
|
||||
* Tests for {@link HeaderWriterLogoutHandler} that passing
|
||||
* {@link ClearSiteDataHeaderWriter} implementation.
|
||||
*
|
||||
* @author Rafiullah Hamedy
|
||||
*
|
||||
@@ -55,8 +55,7 @@ public class LogoutConfigurerClearSiteDataTests {
|
||||
|
||||
private static final String CLEAR_SITE_DATA_HEADER = "Clear-Site-Data";
|
||||
|
||||
private static final ClearSiteDataHeaderWriter.Directive[] SOURCE =
|
||||
{ CACHE, COOKIES, STORAGE, EXECUTION_CONTEXTS };
|
||||
private static final ClearSiteDataHeaderWriter.Directive[] SOURCE = { CACHE, COOKIES, STORAGE, EXECUTION_CONTEXTS };
|
||||
|
||||
private static final String HEADER_VALUE = "\"cache\", \"cookies\", \"storage\", \"executionContexts\"";
|
||||
|
||||
@@ -72,7 +71,7 @@ public class LogoutConfigurerClearSiteDataTests {
|
||||
this.spring.register(HttpLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/logout").secure(true).with(csrf()))
|
||||
.andExpect(header().doesNotExist(CLEAR_SITE_DATA_HEADER));
|
||||
.andExpect(header().doesNotExist(CLEAR_SITE_DATA_HEADER));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -80,8 +79,7 @@ public class LogoutConfigurerClearSiteDataTests {
|
||||
public void logoutWhenRequestTypePostAndNotSecureThenHeaderNotPresent() throws Exception {
|
||||
this.spring.register(HttpLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout").with(csrf()))
|
||||
.andExpect(header().doesNotExist(CLEAR_SITE_DATA_HEADER));
|
||||
this.mvc.perform(post("/logout").with(csrf())).andExpect(header().doesNotExist(CLEAR_SITE_DATA_HEADER));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -90,11 +88,12 @@ public class LogoutConfigurerClearSiteDataTests {
|
||||
this.spring.register(HttpLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout").secure(true).with(csrf()))
|
||||
.andExpect(header().stringValues(CLEAR_SITE_DATA_HEADER, HEADER_VALUE));
|
||||
.andExpect(header().stringValues(CLEAR_SITE_DATA_HEADER, HEADER_VALUE));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class HttpLogoutConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -103,5 +102,7 @@ public class LogoutConfigurerClearSiteDataTests {
|
||||
.addLogoutHandler(new HeaderWriterLogoutHandler(new ClearSiteDataHeaderWriter(SOURCE)));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -66,12 +66,12 @@ public class LogoutConfigurerTests {
|
||||
@Test
|
||||
public void configureWhenDefaultLogoutSuccessHandlerForHasNullLogoutHandlerThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullLogoutSuccessHandlerConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullLogoutSuccessHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -80,17 +80,18 @@ public class LogoutConfigurerTests {
|
||||
.defaultLogoutSuccessHandlerFor(null, mock(RequestMatcher.class));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenDefaultLogoutSuccessHandlerForHasNullLogoutHandlerInLambdaThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullLogoutSuccessHandlerInLambdaConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullLogoutSuccessHandlerInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -100,17 +101,18 @@ public class LogoutConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenDefaultLogoutSuccessHandlerForHasNullMatcherThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullMatcherConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullMatcherConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -119,17 +121,18 @@ public class LogoutConfigurerTests {
|
||||
.defaultLogoutSuccessHandlerFor(mock(LogoutSuccessHandler.class), null);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenDefaultLogoutSuccessHandlerForHasNullMatcherInLambdaThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullMatcherInLambdaConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullMatcherInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -139,18 +142,19 @@ public class LogoutConfigurerTests {
|
||||
);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenRegisteringObjectPostProcessorThenInvokedOnLogoutFilter() {
|
||||
this.spring.register(ObjectPostProcessorConfig.class).autowire();
|
||||
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor)
|
||||
.postProcess(any(LogoutFilter.class));
|
||||
verify(ObjectPostProcessorConfig.objectPostProcessor).postProcess(any(LogoutFilter.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class ObjectPostProcessorConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static ObjectPostProcessor<Object> objectPostProcessor = spy(ReflectingObjectPostProcessor.class);
|
||||
|
||||
@Override
|
||||
@@ -165,27 +169,29 @@ public class LogoutConfigurerTests {
|
||||
static ObjectPostProcessor<Object> objectPostProcessor() {
|
||||
return objectPostProcessor;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class ReflectingObjectPostProcessor implements ObjectPostProcessor<Object> {
|
||||
|
||||
@Override
|
||||
public <O> O postProcess(O object) {
|
||||
return object;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenInvokedTwiceThenUsesOriginalLogoutUrl() throws Exception {
|
||||
this.spring.register(DuplicateDoesNotOverrideConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/custom/logout")
|
||||
.with(csrf()))
|
||||
.andExpect(status().isFound())
|
||||
this.mvc.perform(post("/custom/logout").with(csrf())).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class DuplicateDoesNotOverrideConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -204,6 +210,7 @@ public class LogoutConfigurerTests {
|
||||
.inMemoryAuthentication();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-2311
|
||||
@@ -211,36 +218,28 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenGetRequestAndCsrfDisabledThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(get("/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenPostRequestAndCsrfDisabledThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(post("/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenPutRequestAndCsrfDisabledThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(put("/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(put("/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenDeleteRequestAndCsrfDisabledThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(delete("/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(delete("/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -255,23 +254,21 @@ public class LogoutConfigurerTests {
|
||||
.logout();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenGetRequestAndCsrfDisabledAndCustomLogoutUrlThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledAndCustomLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/custom/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(get("/custom/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenPostRequestAndCsrfDisabledAndCustomLogoutUrlThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledAndCustomLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/custom/logout"))
|
||||
.andExpect(status().isFound())
|
||||
this.mvc.perform(post("/custom/logout")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@@ -279,17 +276,14 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenPutRequestAndCsrfDisabledAndCustomLogoutUrlThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledAndCustomLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(put("/custom/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(put("/custom/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenDeleteRequestAndCsrfDisabledAndCustomLogoutUrlThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledAndCustomLogoutConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(delete("/custom/logout"))
|
||||
.andExpect(status().isFound())
|
||||
this.mvc.perform(delete("/custom/logout")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@@ -306,15 +300,14 @@ public class LogoutConfigurerTests {
|
||||
.logoutUrl("/custom/logout");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenCustomLogoutUrlInLambdaThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(CsrfDisabledAndCustomLogoutInLambdaConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/custom/logout"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(get("/custom/logout")).andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -329,18 +322,19 @@ public class LogoutConfigurerTests {
|
||||
.logout(logout -> logout.logoutUrl("/custom/logout"));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-3170
|
||||
@Test
|
||||
public void configureWhenLogoutHandlerNullThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullLogoutHandlerConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullLogoutHandlerConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -349,17 +343,18 @@ public class LogoutConfigurerTests {
|
||||
.addLogoutHandler(null);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void configureWhenLogoutHandlerNullInLambdaThenException() {
|
||||
assertThatThrownBy(() -> this.spring.register(NullLogoutHandlerInLambdaConfig.class).autowire())
|
||||
.isInstanceOf(BeanCreationException.class)
|
||||
.hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
.isInstanceOf(BeanCreationException.class).hasRootCauseInstanceOf(IllegalArgumentException.class);
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NullLogoutHandlerInLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -367,6 +362,7 @@ public class LogoutConfigurerTests {
|
||||
.logout(logout -> logout.addLogoutHandler(null));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// SEC-3170
|
||||
@@ -374,14 +370,13 @@ public class LogoutConfigurerTests {
|
||||
public void rememberMeWhenRememberMeServicesNotLogoutHandlerThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(RememberMeNoLogoutHandler.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf()))
|
||||
.andExpect(status().isFound())
|
||||
this.mvc.perform(post("/logout").with(csrf())).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class RememberMeNoLogoutHandler extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static RememberMeServices REMEMBER_ME = mock(RememberMeServices.class);
|
||||
|
||||
@Override
|
||||
@@ -392,18 +387,16 @@ public class LogoutConfigurerTests {
|
||||
.rememberMeServices(REMEMBER_ME);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenAcceptTextHtmlThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(BasicSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf())
|
||||
.with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, MediaType.TEXT_HTML_VALUE))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(
|
||||
post("/logout").with(csrf()).with(user("user")).header(HttpHeaders.ACCEPT, MediaType.TEXT_HTML_VALUE))
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
// gh-3282
|
||||
@@ -411,11 +404,8 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenAcceptApplicationJsonThenReturnsStatusNoContent() throws Exception {
|
||||
this.spring.register(BasicSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf())
|
||||
.with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE))
|
||||
.andExpect(status().isNoContent());
|
||||
this.mvc.perform(post("/logout").with(csrf()).with(user("user")).header(HttpHeaders.ACCEPT,
|
||||
MediaType.APPLICATION_JSON_VALUE)).andExpect(status().isNoContent());
|
||||
}
|
||||
|
||||
// gh-4831
|
||||
@@ -423,10 +413,8 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenAcceptAllThenReturnsStatusNoContent() throws Exception {
|
||||
this.spring.register(BasicSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf())
|
||||
.with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, MediaType.ALL_VALUE))
|
||||
this.mvc.perform(
|
||||
post("/logout").with(csrf()).with(user("user")).header(HttpHeaders.ACCEPT, MediaType.ALL_VALUE))
|
||||
.andExpect(status().isNoContent());
|
||||
}
|
||||
|
||||
@@ -435,11 +423,9 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenAcceptFromChromeThenRedirectsToLogin() throws Exception {
|
||||
this.spring.register(BasicSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf()).with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?logout"));
|
||||
this.mvc.perform(post("/logout").with(csrf()).with(user("user")).header(HttpHeaders.ACCEPT,
|
||||
"text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8"))
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/login?logout"));
|
||||
}
|
||||
|
||||
// gh-3997
|
||||
@@ -447,29 +433,26 @@ public class LogoutConfigurerTests {
|
||||
public void logoutWhenXMLHttpRequestThenReturnsStatusNoContent() throws Exception {
|
||||
this.spring.register(BasicSecurityConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf())
|
||||
.with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, "text/html,application/json")
|
||||
.header("X-Requested-With", "XMLHttpRequest"))
|
||||
this.mvc.perform(post("/logout").with(csrf()).with(user("user"))
|
||||
.header(HttpHeaders.ACCEPT, "text/html,application/json").header("X-Requested-With", "XMLHttpRequest"))
|
||||
.andExpect(status().isNoContent());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class BasicSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void logoutWhenDisabledThenLogoutUrlNotFound() throws Exception {
|
||||
this.spring.register(LogoutDisabledConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(post("/logout")
|
||||
.with(csrf()))
|
||||
.andExpect(status().isNotFound());
|
||||
this.mvc.perform(post("/logout").with(csrf())).andExpect(status().isNotFound());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class LogoutDisabledConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -478,5 +461,7 @@ public class LogoutConfigurerTests {
|
||||
.disable();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -45,6 +45,7 @@ import static org.springframework.test.web.servlet.request.MockMvcRequestBuilder
|
||||
* @author Josh Cummings
|
||||
*/
|
||||
public class NamespaceDebugTests {
|
||||
|
||||
@Rule
|
||||
public final SpringTestRule spring = new SpringTestRule();
|
||||
|
||||
@@ -60,8 +61,9 @@ public class NamespaceDebugTests {
|
||||
verify(appender, atLeastOnce()).doAppend(any(ILoggingEvent.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity(debug=true)
|
||||
@EnableWebSecurity(debug = true)
|
||||
static class DebugWebSecurity extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -75,6 +77,7 @@ public class NamespaceDebugTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NoDebugWebSecurity extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
private Appender<ILoggingEvent> mockAppenderFor(String name) {
|
||||
@@ -88,4 +91,5 @@ public class NamespaceDebugTests {
|
||||
private Class<?> filterChainClass() {
|
||||
return this.spring.getContext().getBean("springSecurityFilterChain").getClass();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -57,12 +57,12 @@ public class NamespaceHttpAnonymousTests {
|
||||
public void anonymousRequestWhenUsingDefaultAnonymousConfigurationThenUsesAnonymousAuthentication()
|
||||
throws Exception {
|
||||
this.spring.register(AnonymousConfig.class, AnonymousController.class).autowire();
|
||||
this.mvc.perform(get("/type"))
|
||||
.andExpect(content().string(AnonymousAuthenticationToken.class.getSimpleName()));
|
||||
this.mvc.perform(get("/type")).andExpect(content().string(AnonymousAuthenticationToken.class.getSimpleName()));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -72,18 +72,18 @@ public class NamespaceHttpAnonymousTests {
|
||||
.anyRequest().denyAll();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void anonymousRequestWhenDisablingAnonymousThenDenies()
|
||||
throws Exception {
|
||||
public void anonymousRequestWhenDisablingAnonymousThenDenies() throws Exception {
|
||||
this.spring.register(AnonymousDisabledConfig.class, AnonymousController.class).autowire();
|
||||
this.mvc.perform(get("/type"))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/type")).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousDisabledConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -103,18 +103,18 @@ public class NamespaceHttpAnonymousTests {
|
||||
.withUser(PasswordEncodedUser.admin());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestWhenAnonymousThenSendsAnonymousConfiguredAuthorities()
|
||||
throws Exception {
|
||||
public void requestWhenAnonymousThenSendsAnonymousConfiguredAuthorities() throws Exception {
|
||||
this.spring.register(AnonymousGrantedAuthorityConfig.class, AnonymousController.class).autowire();
|
||||
this.mvc.perform(get("/type"))
|
||||
.andExpect(content().string(AnonymousAuthenticationToken.class.getSimpleName()));
|
||||
this.mvc.perform(get("/type")).andExpect(content().string(AnonymousAuthenticationToken.class.getSimpleName()));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousGrantedAuthorityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -127,17 +127,18 @@ public class NamespaceHttpAnonymousTests {
|
||||
.authorities("ROLE_ANON");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void anonymousRequestWhenAnonymousKeyConfiguredThenKeyIsUsed() throws Exception {
|
||||
this.spring.register(AnonymousKeyConfig.class, AnonymousController.class).autowire();
|
||||
this.mvc.perform(get("/key"))
|
||||
.andExpect(content().string(String.valueOf("AnonymousKeyConfig".hashCode())));
|
||||
this.mvc.perform(get("/key")).andExpect(content().string(String.valueOf("AnonymousKeyConfig".hashCode())));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousKeyConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -149,17 +150,18 @@ public class NamespaceHttpAnonymousTests {
|
||||
.anonymous().key("AnonymousKeyConfig");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void anonymousRequestWhenAnonymousUsernameConfiguredThenUsernameIsUsed() throws Exception {
|
||||
this.spring.register(AnonymousUsernameConfig.class, AnonymousController.class).autowire();
|
||||
this.mvc.perform(get("/principal"))
|
||||
.andExpect(content().string("AnonymousUsernameConfig"));
|
||||
this.mvc.perform(get("/principal")).andExpect(content().string("AnonymousUsernameConfig"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AnonymousUsernameConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -171,39 +173,33 @@ public class NamespaceHttpAnonymousTests {
|
||||
.anonymous().principal("AnonymousUsernameConfig");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class AnonymousController {
|
||||
|
||||
@GetMapping("/type")
|
||||
String type() {
|
||||
return anonymousToken()
|
||||
.map(AnonymousAuthenticationToken::getClass)
|
||||
.map(Class::getSimpleName)
|
||||
.orElse(null);
|
||||
return anonymousToken().map(AnonymousAuthenticationToken::getClass).map(Class::getSimpleName).orElse(null);
|
||||
}
|
||||
|
||||
@GetMapping("/key")
|
||||
String key() {
|
||||
return anonymousToken()
|
||||
.map(AnonymousAuthenticationToken::getKeyHash)
|
||||
.map(String::valueOf)
|
||||
.orElse(null);
|
||||
return anonymousToken().map(AnonymousAuthenticationToken::getKeyHash).map(String::valueOf).orElse(null);
|
||||
}
|
||||
|
||||
@GetMapping("/principal")
|
||||
String principal() {
|
||||
return anonymousToken()
|
||||
.map(AnonymousAuthenticationToken::getName)
|
||||
.orElse(null);
|
||||
return anonymousToken().map(AnonymousAuthenticationToken::getName).orElse(null);
|
||||
}
|
||||
|
||||
Optional<AnonymousAuthenticationToken> anonymousToken() {
|
||||
return Optional.of(SecurityContextHolder.getContext())
|
||||
.map(SecurityContext::getAuthentication)
|
||||
return Optional.of(SecurityContextHolder.getContext()).map(SecurityContext::getAuthentication)
|
||||
.filter(a -> a instanceof AnonymousAuthenticationToken)
|
||||
.map(AnonymousAuthenticationToken.class::cast);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -65,25 +65,21 @@ public class NamespaceHttpBasicTests {
|
||||
public void basicAuthenticationWhenUsingDefaultsThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(HttpBasicConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string(HttpHeaders.WWW_AUTHENTICATE, "Basic realm=\"Realm\""));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")))
|
||||
.andExpect(status().isNotFound());
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password"))).andExpect(status().isNotFound());
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class UserConfig {
|
||||
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
return new InMemoryUserDetailsManager(
|
||||
// @formatter:off
|
||||
// @formatter:off
|
||||
User.withDefaultPasswordEncoder()
|
||||
.username("user")
|
||||
.password("password")
|
||||
@@ -92,10 +88,12 @@ public class NamespaceHttpBasicTests {
|
||||
// @formatter:on
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class HttpBasicConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -105,27 +103,24 @@ public class NamespaceHttpBasicTests {
|
||||
.httpBasic();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void basicAuthenticationWhenUsingDefaultsInLambdaThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(HttpBasicLambdaConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().isUnauthorized());
|
||||
this.mvc.perform(get("/")).andExpect(status().isUnauthorized());
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string(HttpHeaders.WWW_AUTHENTICATE, "Basic realm=\"Realm\""));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")))
|
||||
.andExpect(status().isNotFound());
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password"))).andExpect(status().isNotFound());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class HttpBasicLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -136,6 +131,7 @@ public class NamespaceHttpBasicTests {
|
||||
.httpBasic(withDefaults());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -145,14 +141,13 @@ public class NamespaceHttpBasicTests {
|
||||
public void basicAuthenticationWhenUsingCustomRealmThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(CustomHttpBasicConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string(HttpHeaders.WWW_AUTHENTICATE, "Basic realm=\"Custom Realm\""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomHttpBasicConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -163,20 +158,20 @@ public class NamespaceHttpBasicTests {
|
||||
.httpBasic().realmName("Custom Realm");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void basicAuthenticationWhenUsingCustomRealmInLambdaThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(CustomHttpBasicLambdaConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().isUnauthorized())
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().isUnauthorized())
|
||||
.andExpect(header().string(HttpHeaders.WWW_AUTHENTICATE, "Basic realm=\"Custom Realm\""));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomHttpBasicLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -188,6 +183,7 @@ public class NamespaceHttpBasicTests {
|
||||
.httpBasic(httpBasicConfig -> httpBasicConfig.realmName("Custom Realm"));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -197,19 +193,19 @@ public class NamespaceHttpBasicTests {
|
||||
public void basicAuthenticationWhenUsingAuthenticationDetailsSourceRefThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(AuthenticationDetailsSourceHttpBasicConfig.class, UserConfig.class).autowire();
|
||||
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> source =
|
||||
this.spring.getContext().getBean(AuthenticationDetailsSource.class);
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> source = this.spring.getContext()
|
||||
.getBean(AuthenticationDetailsSource.class);
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")));
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password")));
|
||||
|
||||
verify(source).buildDetails(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthenticationDetailsSourceHttpBasicConfig extends WebSecurityConfigurerAdapter {
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource =
|
||||
mock(AuthenticationDetailsSource.class);
|
||||
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource = mock(
|
||||
AuthenticationDetailsSource.class);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -224,6 +220,7 @@ public class NamespaceHttpBasicTests {
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource() {
|
||||
return this.authenticationDetailsSource;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -231,19 +228,19 @@ public class NamespaceHttpBasicTests {
|
||||
throws Exception {
|
||||
this.spring.register(AuthenticationDetailsSourceHttpBasicLambdaConfig.class, UserConfig.class).autowire();
|
||||
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> source =
|
||||
this.spring.getContext().getBean(AuthenticationDetailsSource.class);
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> source = this.spring.getContext()
|
||||
.getBean(AuthenticationDetailsSource.class);
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")));
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password")));
|
||||
|
||||
verify(source).buildDetails(any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class AuthenticationDetailsSourceHttpBasicLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource =
|
||||
mock(AuthenticationDetailsSource.class);
|
||||
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource = mock(
|
||||
AuthenticationDetailsSource.class);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -258,6 +255,7 @@ public class NamespaceHttpBasicTests {
|
||||
AuthenticationDetailsSource<HttpServletRequest, ?> authenticationDetailsSource() {
|
||||
return this.authenticationDetailsSource;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -267,22 +265,17 @@ public class NamespaceHttpBasicTests {
|
||||
public void basicAuthenticationWhenUsingEntryPointRefThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(EntryPointRefHttpBasicConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().is(999));
|
||||
this.mvc.perform(get("/")).andExpect(status().is(999));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().is(999));
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().is(999));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")))
|
||||
.andExpect(status().isNotFound());
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password"))).andExpect(status().isNotFound());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EntryPointRefHttpBasicConfig extends WebSecurityConfigurerAdapter {
|
||||
AuthenticationEntryPoint authenticationEntryPoint =
|
||||
(request, response, ex) -> response.setStatus(999);
|
||||
|
||||
AuthenticationEntryPoint authenticationEntryPoint = (request, response, ex) -> response.setStatus(999);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -295,28 +288,24 @@ public class NamespaceHttpBasicTests {
|
||||
.authenticationEntryPoint(this.authenticationEntryPoint);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void basicAuthenticationWhenUsingEntryPointRefInLambdaThenMatchesNamespace() throws Exception {
|
||||
this.spring.register(EntryPointRefHttpBasicLambdaConfig.class, UserConfig.class).autowire();
|
||||
|
||||
this.mvc.perform(get("/"))
|
||||
.andExpect(status().is(999));
|
||||
this.mvc.perform(get("/")).andExpect(status().is(999));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "invalid")))
|
||||
.andExpect(status().is(999));
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "invalid"))).andExpect(status().is(999));
|
||||
|
||||
this.mvc.perform(get("/")
|
||||
.with(httpBasic("user", "password")))
|
||||
.andExpect(status().isNotFound());
|
||||
this.mvc.perform(get("/").with(httpBasic("user", "password"))).andExpect(status().isNotFound());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class EntryPointRefHttpBasicLambdaConfig extends WebSecurityConfigurerAdapter {
|
||||
AuthenticationEntryPoint authenticationEntryPoint =
|
||||
(request, response, ex) -> response.setStatus(999);
|
||||
|
||||
AuthenticationEntryPoint authenticationEntryPoint = (request, response, ex) -> response.setStatus(999);
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
@@ -330,5 +319,7 @@ public class NamespaceHttpBasicTests {
|
||||
httpBasicConfig.authenticationEntryPoint(this.authenticationEntryPoint));
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
package org.springframework.security.config.annotation.web.configurers;
|
||||
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
@@ -66,6 +65,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomFilterBeforeConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -73,6 +73,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -83,6 +84,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomFilterAfterConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
http
|
||||
@@ -90,6 +92,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.formLogin();
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -100,6 +103,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomFilterPositionConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
CustomFilterPositionConfig() {
|
||||
// do not add the default filters to make testing easier
|
||||
super(true);
|
||||
@@ -113,8 +117,8 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.addFilter(new CustomFilter());
|
||||
// @formatter:on
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getFiltersWhenFilterAddedAtPositionThenBehaviorMatchesNamespace() {
|
||||
@@ -124,6 +128,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomFilterPositionAtConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
CustomFilterPositionAtConfig() {
|
||||
// do not add the default filters to make testing easier
|
||||
super(true);
|
||||
@@ -135,6 +140,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.addFilterAt(new OtherCustomFilter(), UsernamePasswordAuthenticationFilter.class);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -145,6 +151,7 @@ public class NamespaceHttpCustomFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class NoAuthenticationManagerInHttpConfigurationConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
NoAuthenticationManagerInHttpConfigurationConfig() {
|
||||
super(true);
|
||||
}
|
||||
@@ -163,14 +170,16 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.addFilterBefore(new CustomFilter(), UsernamePasswordAuthenticationFilter.class);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class UserDetailsServiceConfig {
|
||||
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
return new InMemoryUserDetailsManager(
|
||||
// @formatter:off
|
||||
// @formatter:off
|
||||
User.withDefaultPasswordEncoder()
|
||||
.username("user")
|
||||
.password("password")
|
||||
@@ -178,28 +187,35 @@ public class NamespaceHttpCustomFilterTests {
|
||||
.build());
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class CustomFilter extends UsernamePasswordAuthenticationFilter {
|
||||
|
||||
}
|
||||
|
||||
static class CustomFilter extends UsernamePasswordAuthenticationFilter {}
|
||||
static class OtherCustomFilter extends OncePerRequestFilter {
|
||||
protected void doFilterInternal(
|
||||
HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
|
||||
throws ServletException, IOException {
|
||||
|
||||
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
|
||||
FilterChain filterChain) throws ServletException, IOException {
|
||||
filterChain.doFilter(request, response);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class CustomAuthenticationManager implements AuthenticationManager {
|
||||
public Authentication authenticate(Authentication authentication)
|
||||
throws AuthenticationException {
|
||||
|
||||
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private ListAssert<Class<?>> assertThatFilters() {
|
||||
FilterChainProxy filterChain = this.spring.getContext().getBean(FilterChainProxy.class);
|
||||
List<Class<?>> filters = filterChain.getFilters("/").stream()
|
||||
.map(Object::getClass).collect(Collectors.toList());
|
||||
List<Class<?>> filters = filterChain.getFilters("/").stream().map(Object::getClass)
|
||||
.collect(Collectors.toList());
|
||||
return assertThat(filters);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user