Reformat code using spring-javaformat
Run `./gradlew format` to reformat all java files. Issue gh-8945
This commit is contained in:
+5
-6
@@ -46,7 +46,8 @@ import org.springframework.util.Assert;
|
||||
* </li>
|
||||
* <li>The test is ran. When used with {@link MockMvc} it is typically used with
|
||||
* {@link SecurityMockMvcRequestPostProcessors#testSecurityContext()}. Which ensures the
|
||||
* {@link SecurityContext} from {@link TestSecurityContextHolder} is properly populated.</li>
|
||||
* {@link SecurityContext} from {@link TestSecurityContextHolder} is properly
|
||||
* populated.</li>
|
||||
* <li>After the test is executed, the {@link TestSecurityContextHolder} and the
|
||||
* {@link SecurityContextHolder} are cleared out</li>
|
||||
* </ul>
|
||||
@@ -71,7 +72,6 @@ public final class TestSecurityContextHolder {
|
||||
|
||||
/**
|
||||
* Gets the {@link SecurityContext} from {@link TestSecurityContextHolder}.
|
||||
*
|
||||
* @return the {@link SecurityContext} from {@link TestSecurityContextHolder}.
|
||||
*/
|
||||
public static SecurityContext getContext() {
|
||||
@@ -97,10 +97,9 @@ public final class TestSecurityContextHolder {
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new {@link SecurityContext} with the given {@link Authentication}.
|
||||
* The {@link SecurityContext} is set on {@link TestSecurityContextHolder} and
|
||||
* Creates a new {@link SecurityContext} with the given {@link Authentication}. The
|
||||
* {@link SecurityContext} is set on {@link TestSecurityContextHolder} and
|
||||
* {@link SecurityContextHolder}.
|
||||
*
|
||||
* @param authentication the {@link Authentication} to use
|
||||
* @since 5.1.1
|
||||
*/
|
||||
@@ -114,7 +113,6 @@ public final class TestSecurityContextHolder {
|
||||
/**
|
||||
* Gets the default {@link SecurityContext} by delegating to the
|
||||
* {@link SecurityContextHolder}
|
||||
*
|
||||
* @return the default {@link SecurityContext}
|
||||
*/
|
||||
private static SecurityContext getDefaultContext() {
|
||||
@@ -123,4 +121,5 @@ public final class TestSecurityContextHolder {
|
||||
|
||||
private TestSecurityContextHolder() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-7
@@ -28,11 +28,10 @@ import org.springframework.security.test.context.support.WithSecurityContextTest
|
||||
import org.springframework.test.context.TestExecutionListeners;
|
||||
|
||||
/**
|
||||
* There are many times a user may want to use Spring Security's test support
|
||||
* (i.e. WithMockUser) but have no need for any other
|
||||
* {@link TestExecutionListeners} (i.e. no need to setup an
|
||||
* {@link ApplicationContext}). This annotation is a meta annotation that only
|
||||
* enables Spring Security's {@link TestExecutionListeners}.
|
||||
* There are many times a user may want to use Spring Security's test support (i.e.
|
||||
* WithMockUser) but have no need for any other {@link TestExecutionListeners} (i.e. no
|
||||
* need to setup an {@link ApplicationContext}). This annotation is a meta annotation that
|
||||
* only enables Spring Security's {@link TestExecutionListeners}.
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @since 4.0.2
|
||||
@@ -43,7 +42,8 @@ import org.springframework.test.context.TestExecutionListeners;
|
||||
@Inherited
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.TYPE)
|
||||
@TestExecutionListeners(inheritListeners = false, listeners = {WithSecurityContextTestExecutionListener.class,
|
||||
ReactorContextTestExecutionListener.class})
|
||||
@TestExecutionListeners(inheritListeners = false,
|
||||
listeners = { WithSecurityContextTestExecutionListener.class, ReactorContextTestExecutionListener.class })
|
||||
public @interface SecurityTestExecutionListeners {
|
||||
|
||||
}
|
||||
|
||||
+2
-2
@@ -25,8 +25,7 @@ import org.springframework.util.Assert;
|
||||
* @author Rob Winch
|
||||
* @since 5.0
|
||||
*/
|
||||
class DelegatingTestExecutionListener
|
||||
extends AbstractTestExecutionListener {
|
||||
class DelegatingTestExecutionListener extends AbstractTestExecutionListener {
|
||||
|
||||
private final TestExecutionListener delegate;
|
||||
|
||||
@@ -69,4 +68,5 @@ class DelegatingTestExecutionListener
|
||||
public void afterTestClass(TestContext testContext) throws Exception {
|
||||
delegate.afterTestClass(testContext);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+16
-9
@@ -40,10 +40,10 @@ import reactor.util.context.Context;
|
||||
* @see WithSecurityContextTestExecutionListener
|
||||
* @see org.springframework.security.test.context.annotation.SecurityTestExecutionListeners
|
||||
*/
|
||||
public class ReactorContextTestExecutionListener
|
||||
extends DelegatingTestExecutionListener {
|
||||
public class ReactorContextTestExecutionListener extends DelegatingTestExecutionListener {
|
||||
|
||||
private static final String HOOKS_CLASS_NAME = "reactor.core.publisher.Hooks";
|
||||
|
||||
private static final String CONTEXT_OPERATOR_KEY = SecurityContext.class.getName();
|
||||
|
||||
public ReactorContextTestExecutionListener() {
|
||||
@@ -51,16 +51,18 @@ public class ReactorContextTestExecutionListener
|
||||
}
|
||||
|
||||
private static TestExecutionListener createDelegate() {
|
||||
return ClassUtils.isPresent(HOOKS_CLASS_NAME, ReactorContextTestExecutionListener.class.getClassLoader()) ?
|
||||
new DelegateTestExecutionListener() :
|
||||
new AbstractTestExecutionListener() {};
|
||||
return ClassUtils.isPresent(HOOKS_CLASS_NAME, ReactorContextTestExecutionListener.class.getClassLoader())
|
||||
? new DelegateTestExecutionListener() : new AbstractTestExecutionListener() {
|
||||
};
|
||||
}
|
||||
|
||||
private static class DelegateTestExecutionListener extends AbstractTestExecutionListener {
|
||||
|
||||
@Override
|
||||
public void beforeTestMethod(TestContext testContext) {
|
||||
SecurityContext securityContext = TestSecurityContextHolder.getContext();
|
||||
Hooks.onLastOperator(CONTEXT_OPERATOR_KEY, Operators.lift((s, sub) -> new SecuritySubContext<>(sub, securityContext)));
|
||||
Hooks.onLastOperator(CONTEXT_OPERATOR_KEY,
|
||||
Operators.lift((s, sub) -> new SecuritySubContext<>(sub, securityContext)));
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -69,9 +71,12 @@ public class ReactorContextTestExecutionListener
|
||||
}
|
||||
|
||||
private static class SecuritySubContext<T> implements CoreSubscriber<T> {
|
||||
private static String CONTEXT_DEFAULTED_ATTR_NAME = SecuritySubContext.class.getName().concat(".CONTEXT_DEFAULTED_ATTR_NAME");
|
||||
|
||||
private static String CONTEXT_DEFAULTED_ATTR_NAME = SecuritySubContext.class.getName()
|
||||
.concat(".CONTEXT_DEFAULTED_ATTR_NAME");
|
||||
|
||||
private final CoreSubscriber<T> delegate;
|
||||
|
||||
private final SecurityContext securityContext;
|
||||
|
||||
SecuritySubContext(CoreSubscriber<T> delegate, SecurityContext securityContext) {
|
||||
@@ -90,8 +95,7 @@ public class ReactorContextTestExecutionListener
|
||||
if (authentication == null) {
|
||||
return context;
|
||||
}
|
||||
Context toMerge = ReactiveSecurityContextHolder.withSecurityContext(
|
||||
Mono.just(this.securityContext));
|
||||
Context toMerge = ReactiveSecurityContextHolder.withSecurityContext(Mono.just(this.securityContext));
|
||||
return toMerge.putAll(context);
|
||||
}
|
||||
|
||||
@@ -114,7 +118,9 @@ public class ReactorContextTestExecutionListener
|
||||
public void onComplete() {
|
||||
delegate.onComplete();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -124,4 +130,5 @@ public class ReactorContextTestExecutionListener
|
||||
public int getOrder() {
|
||||
return 11000;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+8
-3
@@ -19,20 +19,25 @@ package org.springframework.security.test.context.support;
|
||||
import org.springframework.test.context.TestContext;
|
||||
|
||||
/**
|
||||
* Represents the events on the methods of {@link org.springframework.test.context.TestExecutionListener}
|
||||
* Represents the events on the methods of
|
||||
* {@link org.springframework.test.context.TestExecutionListener}
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @since 5.1
|
||||
*/
|
||||
public enum TestExecutionEvent {
|
||||
|
||||
/**
|
||||
* Associated to {@link org.springframework.test.context.TestExecutionListener#beforeTestMethod(TestContext)}
|
||||
* Associated to
|
||||
* {@link org.springframework.test.context.TestExecutionListener#beforeTestMethod(TestContext)}
|
||||
* event.
|
||||
*/
|
||||
TEST_METHOD,
|
||||
/**
|
||||
* Associated to {@link org.springframework.test.context.TestExecutionListener#beforeTestExecution(TestContext)}
|
||||
* Associated to
|
||||
* {@link org.springframework.test.context.TestExecutionListener#beforeTestExecution(TestContext)}
|
||||
* event.
|
||||
*/
|
||||
TEST_EXECUTION
|
||||
|
||||
}
|
||||
|
||||
+8
-8
@@ -28,12 +28,12 @@ import org.springframework.security.core.context.SecurityContext;
|
||||
import org.springframework.test.context.TestContext;
|
||||
|
||||
/**
|
||||
* When used with {@link WithSecurityContextTestExecutionListener} this
|
||||
* annotation can be added to a test method to emulate running with an anonymous
|
||||
* user. The {@link SecurityContext} that is used will contain an
|
||||
* {@link AnonymousAuthenticationToken}. This is useful when a user wants to run
|
||||
* a majority of tests as a specific user and wishes to override a few methods
|
||||
* to be anonymous. For example:
|
||||
* When used with {@link WithSecurityContextTestExecutionListener} this annotation can be
|
||||
* added to a test method to emulate running with an anonymous user. The
|
||||
* {@link SecurityContext} that is used will contain an
|
||||
* {@link AnonymousAuthenticationToken}. This is useful when a user wants to run a
|
||||
* majority of tests as a specific user and wishes to override a few methods to be
|
||||
* anonymous. For example:
|
||||
*
|
||||
* <pre>
|
||||
* <code>
|
||||
@@ -47,8 +47,7 @@ import org.springframework.test.context.TestContext;
|
||||
*
|
||||
* // ... lots of tests ran with a default user ...
|
||||
* }
|
||||
* </code>
|
||||
* </pre>
|
||||
* </code> </pre>
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @since 4.1
|
||||
@@ -69,4 +68,5 @@ public @interface WithAnonymousUser {
|
||||
*/
|
||||
@AliasFor(annotation = WithSecurityContext.class)
|
||||
TestExecutionEvent setupBefore() default TestExecutionEvent.TEST_METHOD;
|
||||
|
||||
}
|
||||
|
||||
+4
-5
@@ -25,17 +25,15 @@ import org.springframework.security.core.context.SecurityContext;
|
||||
import org.springframework.security.core.context.SecurityContextHolder;
|
||||
|
||||
/**
|
||||
* A {@link WithAnonymousUserSecurityContextFactory} that runs with an {@link AnonymousAuthenticationToken}.
|
||||
* .
|
||||
* A {@link WithAnonymousUserSecurityContextFactory} that runs with an
|
||||
* {@link AnonymousAuthenticationToken}. .
|
||||
*
|
||||
* @see WithUserDetails
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @since 4.1
|
||||
*/
|
||||
|
||||
final class WithAnonymousUserSecurityContextFactory implements
|
||||
WithSecurityContextFactory<WithAnonymousUser> {
|
||||
final class WithAnonymousUserSecurityContextFactory implements WithSecurityContextFactory<WithAnonymousUser> {
|
||||
|
||||
public SecurityContext createSecurityContext(WithAnonymousUser withUser) {
|
||||
List<GrantedAuthority> authorities = AuthorityUtils.createAuthorityList("ROLE_ANONYMOUS");
|
||||
@@ -44,4 +42,5 @@ final class WithAnonymousUserSecurityContextFactory implements
|
||||
context.setAuthentication(authentication);
|
||||
return context;
|
||||
}
|
||||
|
||||
}
|
||||
+4
-3
@@ -56,6 +56,7 @@ import org.springframework.test.web.servlet.MockMvc;
|
||||
@Documented
|
||||
@WithSecurityContext(factory = WithMockUserSecurityContextFactory.class)
|
||||
public @interface WithMockUser {
|
||||
|
||||
/**
|
||||
* Convenience mechanism for specifying the username. The default is "user". If
|
||||
* {@link #username()} is specified it will be used instead of {@link #value()}
|
||||
@@ -78,9 +79,9 @@ public @interface WithMockUser {
|
||||
* with "ROLE_". For example, the default will result in "ROLE_USER" being used.
|
||||
* </p>
|
||||
* <p>
|
||||
* If {@link #authorities()} is specified this property cannot be changed from the default.
|
||||
* If {@link #authorities()} is specified this property cannot be changed from the
|
||||
* default.
|
||||
* </p>
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String[] roles() default { "USER" };
|
||||
@@ -94,7 +95,6 @@ public @interface WithMockUser {
|
||||
* If this property is specified then {@link #roles()} is not used. This differs from
|
||||
* {@link #roles()} in that it does not prefix the values passed in automatically.
|
||||
* </p>
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String[] authorities() default {};
|
||||
@@ -114,4 +114,5 @@ public @interface WithMockUser {
|
||||
*/
|
||||
@AliasFor(annotation = WithSecurityContext.class)
|
||||
TestExecutionEvent setupBefore() default TestExecutionEvent.TEST_METHOD;
|
||||
|
||||
}
|
||||
|
||||
+13
-14
@@ -35,15 +35,13 @@ import org.springframework.util.StringUtils;
|
||||
* @since 4.0
|
||||
* @see WithMockUser
|
||||
*/
|
||||
final class WithMockUserSecurityContextFactory implements
|
||||
WithSecurityContextFactory<WithMockUser> {
|
||||
final class WithMockUserSecurityContextFactory implements WithSecurityContextFactory<WithMockUser> {
|
||||
|
||||
public SecurityContext createSecurityContext(WithMockUser withUser) {
|
||||
String username = StringUtils.hasLength(withUser.username()) ? withUser
|
||||
.username() : withUser.value();
|
||||
String username = StringUtils.hasLength(withUser.username()) ? withUser.username() : withUser.value();
|
||||
if (username == null) {
|
||||
throw new IllegalArgumentException(withUser
|
||||
+ " cannot have null username on both username and value properties");
|
||||
throw new IllegalArgumentException(
|
||||
withUser + " cannot have null username on both username and value properties");
|
||||
}
|
||||
|
||||
List<GrantedAuthority> grantedAuthorities = new ArrayList<>();
|
||||
@@ -54,21 +52,22 @@ final class WithMockUserSecurityContextFactory implements
|
||||
if (grantedAuthorities.isEmpty()) {
|
||||
for (String role : withUser.roles()) {
|
||||
if (role.startsWith("ROLE_")) {
|
||||
throw new IllegalArgumentException("roles cannot start with ROLE_ Got "
|
||||
+ role);
|
||||
throw new IllegalArgumentException("roles cannot start with ROLE_ Got " + role);
|
||||
}
|
||||
grantedAuthorities.add(new SimpleGrantedAuthority("ROLE_" + role));
|
||||
}
|
||||
} else if (!(withUser.roles().length == 1 && "USER".equals(withUser.roles()[0]))) {
|
||||
throw new IllegalStateException("You cannot define roles attribute "+ Arrays.asList(withUser.roles())+" with authorities attribute "+ Arrays.asList(withUser.authorities()));
|
||||
}
|
||||
else if (!(withUser.roles().length == 1 && "USER".equals(withUser.roles()[0]))) {
|
||||
throw new IllegalStateException("You cannot define roles attribute " + Arrays.asList(withUser.roles())
|
||||
+ " with authorities attribute " + Arrays.asList(withUser.authorities()));
|
||||
}
|
||||
|
||||
User principal = new User(username, withUser.password(), true, true, true, true,
|
||||
grantedAuthorities);
|
||||
Authentication authentication = new UsernamePasswordAuthenticationToken(
|
||||
principal, principal.getPassword(), principal.getAuthorities());
|
||||
User principal = new User(username, withUser.password(), true, true, true, true, grantedAuthorities);
|
||||
Authentication authentication = new UsernamePasswordAuthenticationToken(principal, principal.getPassword(),
|
||||
principal.getAuthorities());
|
||||
SecurityContext context = SecurityContextHolder.createEmptyContext();
|
||||
context.setAuthentication(authentication);
|
||||
return context;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
-1
@@ -54,11 +54,11 @@ import org.springframework.test.context.TestContext;
|
||||
@Inherited
|
||||
@Documented
|
||||
public @interface WithSecurityContext {
|
||||
|
||||
/**
|
||||
* The {@link WithUserDetailsSecurityContextFactory} to use to create the
|
||||
* {@link SecurityContext}. It can contain {@link Autowired} and other Spring
|
||||
* annotations.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
Class<? extends WithSecurityContextFactory<? extends Annotation>> factory();
|
||||
|
||||
+1
-2
@@ -25,7 +25,6 @@ import org.springframework.security.test.context.TestSecurityContextHolder;
|
||||
* {@link SecurityContext} that is populated in the {@link TestSecurityContextHolder}.
|
||||
*
|
||||
* @author Rob Winch
|
||||
*
|
||||
* @param <A>
|
||||
* @see WithSecurityContext
|
||||
* @see WithMockUser
|
||||
@@ -36,10 +35,10 @@ public interface WithSecurityContextFactory<A extends Annotation> {
|
||||
|
||||
/**
|
||||
* Create a {@link SecurityContext} given an Annotation.
|
||||
*
|
||||
* @param annotation the {@link Annotation} to create the {@link SecurityContext}
|
||||
* from. Cannot be null.
|
||||
* @return the {@link SecurityContext} to use. Cannot be null.
|
||||
*/
|
||||
SecurityContext createSecurityContext(A annotation);
|
||||
|
||||
}
|
||||
+31
-37
@@ -47,10 +47,10 @@ import org.springframework.test.web.servlet.MockMvc;
|
||||
* @see ReactorContextTestExecutionListener
|
||||
* @see org.springframework.security.test.context.annotation.SecurityTestExecutionListeners
|
||||
*/
|
||||
public class WithSecurityContextTestExecutionListener
|
||||
extends AbstractTestExecutionListener {
|
||||
public class WithSecurityContextTestExecutionListener extends AbstractTestExecutionListener {
|
||||
|
||||
static final String SECURITY_CONTEXT_ATTR_NAME = WithSecurityContextTestExecutionListener.class.getName().concat(".SECURITY_CONTEXT");
|
||||
static final String SECURITY_CONTEXT_ATTR_NAME = WithSecurityContextTestExecutionListener.class.getName()
|
||||
.concat(".SECURITY_CONTEXT");
|
||||
|
||||
/**
|
||||
* Sets up the {@link SecurityContext} for each test method. First the specific method
|
||||
@@ -60,21 +60,19 @@ public class WithSecurityContextTestExecutionListener
|
||||
*/
|
||||
@Override
|
||||
public void beforeTestMethod(TestContext testContext) {
|
||||
TestSecurityContext testSecurityContext = createTestSecurityContext(
|
||||
testContext.getTestMethod(), testContext);
|
||||
TestSecurityContext testSecurityContext = createTestSecurityContext(testContext.getTestMethod(), testContext);
|
||||
if (testSecurityContext == null) {
|
||||
testSecurityContext = createTestSecurityContext(testContext.getTestClass(),
|
||||
testContext);
|
||||
testSecurityContext = createTestSecurityContext(testContext.getTestClass(), testContext);
|
||||
}
|
||||
if (testSecurityContext == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
Supplier<SecurityContext> supplier = testSecurityContext
|
||||
.getSecurityContextSupplier();
|
||||
Supplier<SecurityContext> supplier = testSecurityContext.getSecurityContextSupplier();
|
||||
if (testSecurityContext.getTestExecutionEvent() == TestExecutionEvent.TEST_METHOD) {
|
||||
TestSecurityContextHolder.setContext(supplier.get());
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
testContext.setAttribute(SECURITY_CONTEXT_ATTR_NAME, supplier);
|
||||
}
|
||||
}
|
||||
@@ -92,19 +90,17 @@ public class WithSecurityContextTestExecutionListener
|
||||
}
|
||||
}
|
||||
|
||||
private TestSecurityContext createTestSecurityContext(AnnotatedElement annotated,
|
||||
TestContext context) {
|
||||
WithSecurityContext withSecurityContext = AnnotatedElementUtils
|
||||
.findMergedAnnotation(annotated, WithSecurityContext.class);
|
||||
private TestSecurityContext createTestSecurityContext(AnnotatedElement annotated, TestContext context) {
|
||||
WithSecurityContext withSecurityContext = AnnotatedElementUtils.findMergedAnnotation(annotated,
|
||||
WithSecurityContext.class);
|
||||
return createTestSecurityContext(annotated, withSecurityContext, context);
|
||||
}
|
||||
|
||||
private TestSecurityContext createTestSecurityContext(Class<?> annotated,
|
||||
TestContext context) {
|
||||
private TestSecurityContext createTestSecurityContext(Class<?> annotated, TestContext context) {
|
||||
MetaAnnotationUtils.AnnotationDescriptor<WithSecurityContext> withSecurityContextDescriptor = MetaAnnotationUtils
|
||||
.findAnnotationDescriptor(annotated, WithSecurityContext.class);
|
||||
WithSecurityContext withSecurityContext = withSecurityContextDescriptor == null
|
||||
? null : withSecurityContextDescriptor.getAnnotation();
|
||||
WithSecurityContext withSecurityContext = withSecurityContextDescriptor == null ? null
|
||||
: withSecurityContextDescriptor.getAnnotation();
|
||||
return createTestSecurityContext(annotated, withSecurityContext, context);
|
||||
}
|
||||
|
||||
@@ -114,35 +110,32 @@ public class WithSecurityContextTestExecutionListener
|
||||
if (withSecurityContext == null) {
|
||||
return null;
|
||||
}
|
||||
withSecurityContext = AnnotationUtils
|
||||
.synthesizeAnnotation(withSecurityContext, annotated);
|
||||
withSecurityContext = AnnotationUtils.synthesizeAnnotation(withSecurityContext, annotated);
|
||||
WithSecurityContextFactory factory = createFactory(withSecurityContext, context);
|
||||
Class<? extends Annotation> type = (Class<? extends Annotation>) GenericTypeResolver
|
||||
.resolveTypeArgument(factory.getClass(),
|
||||
WithSecurityContextFactory.class);
|
||||
.resolveTypeArgument(factory.getClass(), WithSecurityContextFactory.class);
|
||||
Annotation annotation = findAnnotation(annotated, type);
|
||||
Supplier<SecurityContext> supplier = () -> {
|
||||
try {
|
||||
return factory.createSecurityContext(annotation);
|
||||
} catch (RuntimeException e) {
|
||||
throw new IllegalStateException(
|
||||
"Unable to create SecurityContext using " + annotation, e);
|
||||
}
|
||||
catch (RuntimeException e) {
|
||||
throw new IllegalStateException("Unable to create SecurityContext using " + annotation, e);
|
||||
}
|
||||
};
|
||||
TestExecutionEvent initialize = withSecurityContext.setupBefore();
|
||||
return new TestSecurityContext(supplier, initialize);
|
||||
}
|
||||
|
||||
private Annotation findAnnotation(AnnotatedElement annotated,
|
||||
Class<? extends Annotation> type) {
|
||||
private Annotation findAnnotation(AnnotatedElement annotated, Class<? extends Annotation> type) {
|
||||
Annotation findAnnotation = AnnotationUtils.findAnnotation(annotated, type);
|
||||
if (findAnnotation != null) {
|
||||
return findAnnotation;
|
||||
}
|
||||
Annotation[] allAnnotations = AnnotationUtils.getAnnotations(annotated);
|
||||
for (Annotation annotationToTest : allAnnotations) {
|
||||
WithSecurityContext withSecurityContext = AnnotationUtils.findAnnotation(
|
||||
annotationToTest.annotationType(), WithSecurityContext.class);
|
||||
WithSecurityContext withSecurityContext = AnnotationUtils.findAnnotation(annotationToTest.annotationType(),
|
||||
WithSecurityContext.class);
|
||||
if (withSecurityContext != null) {
|
||||
return annotationToTest;
|
||||
}
|
||||
@@ -150,13 +143,11 @@ public class WithSecurityContextTestExecutionListener
|
||||
return null;
|
||||
}
|
||||
|
||||
private WithSecurityContextFactory<? extends Annotation> createFactory(
|
||||
WithSecurityContext withSecurityContext, TestContext testContext) {
|
||||
Class<? extends WithSecurityContextFactory<? extends Annotation>> clazz = withSecurityContext
|
||||
.factory();
|
||||
private WithSecurityContextFactory<? extends Annotation> createFactory(WithSecurityContext withSecurityContext,
|
||||
TestContext testContext) {
|
||||
Class<? extends WithSecurityContextFactory<? extends Annotation>> clazz = withSecurityContext.factory();
|
||||
try {
|
||||
return testContext.getApplicationContext().getAutowireCapableBeanFactory()
|
||||
.createBean(clazz);
|
||||
return testContext.getApplicationContext().getAutowireCapableBeanFactory().createBean(clazz);
|
||||
}
|
||||
catch (IllegalStateException e) {
|
||||
return BeanUtils.instantiateClass(clazz);
|
||||
@@ -184,11 +175,12 @@ public class WithSecurityContextTestExecutionListener
|
||||
}
|
||||
|
||||
static class TestSecurityContext {
|
||||
|
||||
private final Supplier<SecurityContext> securityContextSupplier;
|
||||
|
||||
private final TestExecutionEvent testExecutionEvent;
|
||||
|
||||
TestSecurityContext(Supplier<SecurityContext> securityContextSupplier,
|
||||
TestExecutionEvent testExecutionEvent) {
|
||||
TestSecurityContext(Supplier<SecurityContext> securityContextSupplier, TestExecutionEvent testExecutionEvent) {
|
||||
this.securityContextSupplier = securityContextSupplier;
|
||||
this.testExecutionEvent = testExecutionEvent;
|
||||
}
|
||||
@@ -200,5 +192,7 @@ public class WithSecurityContextTestExecutionListener
|
||||
public TestExecutionEvent getTestExecutionEvent() {
|
||||
return this.testExecutionEvent;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
-4
@@ -55,18 +55,17 @@ import org.springframework.test.web.servlet.MockMvc;
|
||||
@Documented
|
||||
@WithSecurityContext(factory = WithUserDetailsSecurityContextFactory.class)
|
||||
public @interface WithUserDetails {
|
||||
|
||||
/**
|
||||
* The username to look up in the {@link UserDetailsService}
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String value() default "user";
|
||||
|
||||
/**
|
||||
* The bean name for the {@link UserDetailsService} to use. If this is not
|
||||
* provided, then the lookup is done by type and expects only a single
|
||||
* The bean name for the {@link UserDetailsService} to use. If this is not provided,
|
||||
* then the lookup is done by type and expects only a single
|
||||
* {@link UserDetailsService} bean to be exposed.
|
||||
*
|
||||
* @return the bean name for the {@link UserDetailsService} to use.
|
||||
* @since 4.1
|
||||
*/
|
||||
@@ -81,4 +80,5 @@ public @interface WithUserDetails {
|
||||
*/
|
||||
@AliasFor(annotation = WithSecurityContext.class)
|
||||
TestExecutionEvent setupBefore() default TestExecutionEvent.TEST_METHOD;
|
||||
|
||||
}
|
||||
|
||||
+17
-18
@@ -36,15 +36,14 @@ import org.springframework.util.StringUtils;
|
||||
* .
|
||||
*
|
||||
* @see WithUserDetails
|
||||
*
|
||||
* @author Rob Winch
|
||||
* @since 4.0
|
||||
*/
|
||||
|
||||
final class WithUserDetailsSecurityContextFactory implements
|
||||
WithSecurityContextFactory<WithUserDetails> {
|
||||
final class WithUserDetailsSecurityContextFactory implements WithSecurityContextFactory<WithUserDetails> {
|
||||
|
||||
private static final boolean reactorPresent = ClassUtils.isPresent("reactor.core.publisher.Mono", WithUserDetailsSecurityContextFactory.class.getClassLoader());
|
||||
private static final boolean reactorPresent = ClassUtils.isPresent("reactor.core.publisher.Mono",
|
||||
WithUserDetailsSecurityContextFactory.class.getClassLoader());
|
||||
|
||||
private BeanFactory beans;
|
||||
|
||||
@@ -59,8 +58,8 @@ final class WithUserDetailsSecurityContextFactory implements
|
||||
String username = withUser.value();
|
||||
Assert.hasLength(username, "value() must be non empty String");
|
||||
UserDetails principal = userDetailsService.loadUserByUsername(username);
|
||||
Authentication authentication = new UsernamePasswordAuthenticationToken(
|
||||
principal, principal.getPassword(), principal.getAuthorities());
|
||||
Authentication authentication = new UsernamePasswordAuthenticationToken(principal, principal.getPassword(),
|
||||
principal.getAuthorities());
|
||||
SecurityContext context = SecurityContextHolder.createEmptyContext();
|
||||
context.setAuthentication(authentication);
|
||||
return context;
|
||||
@@ -73,35 +72,35 @@ final class WithUserDetailsSecurityContextFactory implements
|
||||
return reactive;
|
||||
}
|
||||
}
|
||||
return StringUtils.hasLength(beanName)
|
||||
? this.beans.getBean(beanName, UserDetailsService.class)
|
||||
: this.beans.getBean(UserDetailsService.class);
|
||||
return StringUtils.hasLength(beanName) ? this.beans.getBean(beanName, UserDetailsService.class)
|
||||
: this.beans.getBean(UserDetailsService.class);
|
||||
}
|
||||
|
||||
public UserDetailsService findAndAdaptReactiveUserDetailsService(String beanName) {
|
||||
try {
|
||||
ReactiveUserDetailsService reactiveUserDetailsService = StringUtils
|
||||
.hasLength(beanName) ?
|
||||
this.beans.getBean(beanName, ReactiveUserDetailsService.class) :
|
||||
this.beans.getBean(ReactiveUserDetailsService.class);
|
||||
ReactiveUserDetailsService reactiveUserDetailsService = StringUtils.hasLength(beanName)
|
||||
? this.beans.getBean(beanName, ReactiveUserDetailsService.class)
|
||||
: this.beans.getBean(ReactiveUserDetailsService.class);
|
||||
return new ReactiveUserDetailsServiceAdapter(reactiveUserDetailsService);
|
||||
} catch(NoSuchBeanDefinitionException | BeanNotOfRequiredTypeException notReactive) {
|
||||
}
|
||||
catch (NoSuchBeanDefinitionException | BeanNotOfRequiredTypeException notReactive) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
private class ReactiveUserDetailsServiceAdapter implements UserDetailsService {
|
||||
|
||||
private final ReactiveUserDetailsService userDetailsService;
|
||||
|
||||
private ReactiveUserDetailsServiceAdapter(
|
||||
ReactiveUserDetailsService userDetailsService) {
|
||||
private ReactiveUserDetailsServiceAdapter(ReactiveUserDetailsService userDetailsService) {
|
||||
this.userDetailsService = userDetailsService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserDetails loadUserByUsername(String username)
|
||||
throws UsernameNotFoundException {
|
||||
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
|
||||
return this.userDetailsService.findByUsername(username).block();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+221
-229
File diff suppressed because it is too large
Load Diff
+26
-28
@@ -42,7 +42,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
/**
|
||||
* Creates a request (including any necessary {@link CsrfToken}) that will submit a
|
||||
* form based login to POST "/login".
|
||||
*
|
||||
* @return the FormLoginRequestBuilder for further customizations
|
||||
*/
|
||||
public static FormLoginRequestBuilder formLogin() {
|
||||
@@ -52,9 +51,7 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
/**
|
||||
* Creates a request (including any necessary {@link CsrfToken}) that will submit a
|
||||
* form based login to POST {@code loginProcessingUrl}.
|
||||
*
|
||||
* @param loginProcessingUrl the URL to POST to
|
||||
*
|
||||
* @return the FormLoginRequestBuilder for further customizations
|
||||
*/
|
||||
public static FormLoginRequestBuilder formLogin(String loginProcessingUrl) {
|
||||
@@ -63,7 +60,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Creates a logout request.
|
||||
*
|
||||
* @return the LogoutRequestBuilder for additional customizations
|
||||
*/
|
||||
public static LogoutRequestBuilder logout() {
|
||||
@@ -73,9 +69,7 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
/**
|
||||
* Creates a logout request (including any necessary {@link CsrfToken}) to the
|
||||
* specified {@code logoutUrl}
|
||||
*
|
||||
* @param logoutUrl the logout request URL
|
||||
*
|
||||
* @return the LogoutRequestBuilder for additional customizations
|
||||
*/
|
||||
public static LogoutRequestBuilder logout(String logoutUrl) {
|
||||
@@ -89,14 +83,17 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
* @since 4.0
|
||||
*/
|
||||
public static final class LogoutRequestBuilder implements RequestBuilder, Mergeable {
|
||||
|
||||
private String logoutUrl = "/logout";
|
||||
|
||||
private RequestPostProcessor postProcessor = csrf();
|
||||
|
||||
private Mergeable parent;
|
||||
|
||||
@Override
|
||||
public MockHttpServletRequest buildRequest(ServletContext servletContext) {
|
||||
MockHttpServletRequestBuilder logoutRequest = post(this.logoutUrl)
|
||||
.accept(MediaType.TEXT_HTML, MediaType.ALL);
|
||||
MockHttpServletRequestBuilder logoutRequest = post(this.logoutUrl).accept(MediaType.TEXT_HTML,
|
||||
MediaType.ALL);
|
||||
|
||||
if (this.parent != null) {
|
||||
logoutRequest = (MockHttpServletRequestBuilder) logoutRequest.merge(this.parent);
|
||||
@@ -110,7 +107,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specifies the logout URL to POST to. Defaults to "/logout".
|
||||
*
|
||||
* @param logoutUrl the logout URL to POST to. Defaults to "/logout".
|
||||
* @return the {@link LogoutRequestBuilder} for additional customizations
|
||||
*/
|
||||
@@ -121,14 +117,12 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specifies the logout URL to POST to.
|
||||
*
|
||||
* @param logoutUrl the logout URL to POST to.
|
||||
* @param uriVars the URI variables
|
||||
* @return the {@link LogoutRequestBuilder} for additional customizations
|
||||
*/
|
||||
public LogoutRequestBuilder logoutUrl(String logoutUrl, Object... uriVars) {
|
||||
this.logoutUrl = UriComponentsBuilder.fromPath(logoutUrl)
|
||||
.buildAndExpand(uriVars).encode().toString();
|
||||
this.logoutUrl = UriComponentsBuilder.fromPath(logoutUrl).buildAndExpand(uriVars).encode().toString();
|
||||
return this;
|
||||
}
|
||||
|
||||
@@ -145,13 +139,15 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
if (parent instanceof Mergeable) {
|
||||
this.parent = (Mergeable) parent;
|
||||
return this;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
throw new IllegalArgumentException("Cannot merge with [" + parent.getClass().getName() + "]");
|
||||
}
|
||||
}
|
||||
|
||||
private LogoutRequestBuilder() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -161,22 +157,27 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
* @since 4.0
|
||||
*/
|
||||
public static final class FormLoginRequestBuilder implements RequestBuilder, Mergeable {
|
||||
|
||||
private String usernameParam = "username";
|
||||
|
||||
private String passwordParam = "password";
|
||||
|
||||
private String username = "user";
|
||||
|
||||
private String password = "password";
|
||||
|
||||
private String loginProcessingUrl = "/login";
|
||||
|
||||
private MediaType acceptMediaType = MediaType.APPLICATION_FORM_URLENCODED;
|
||||
|
||||
private Mergeable parent;
|
||||
|
||||
private RequestPostProcessor postProcessor = csrf();
|
||||
|
||||
@Override
|
||||
public MockHttpServletRequest buildRequest(ServletContext servletContext) {
|
||||
MockHttpServletRequestBuilder loginRequest = post(this.loginProcessingUrl)
|
||||
.accept(this.acceptMediaType)
|
||||
.param(this.usernameParam, this.username)
|
||||
.param(this.passwordParam, this.password);
|
||||
MockHttpServletRequestBuilder loginRequest = post(this.loginProcessingUrl).accept(this.acceptMediaType)
|
||||
.param(this.usernameParam, this.username).param(this.passwordParam, this.password);
|
||||
|
||||
if (this.parent != null) {
|
||||
loginRequest = (MockHttpServletRequestBuilder) loginRequest.merge(this.parent);
|
||||
@@ -190,7 +191,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specifies the URL to POST to. Default is "/login"
|
||||
*
|
||||
* @param loginProcessingUrl the URL to POST to. Default is "/login"
|
||||
* @return the {@link FormLoginRequestBuilder} for additional customizations
|
||||
*/
|
||||
@@ -201,14 +201,13 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specifies the URL to POST to.
|
||||
*
|
||||
* @param loginProcessingUrl the URL to POST to
|
||||
* @param uriVars the URI variables
|
||||
* @return the {@link FormLoginRequestBuilder} for additional customizations
|
||||
*/
|
||||
public FormLoginRequestBuilder loginProcessingUrl(String loginProcessingUrl, Object... uriVars) {
|
||||
this.loginProcessingUrl = UriComponentsBuilder.fromPath(loginProcessingUrl)
|
||||
.buildAndExpand(uriVars).encode().toString();
|
||||
this.loginProcessingUrl = UriComponentsBuilder.fromPath(loginProcessingUrl).buildAndExpand(uriVars).encode()
|
||||
.toString();
|
||||
return this;
|
||||
}
|
||||
|
||||
@@ -256,14 +255,12 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specify both the password parameter name and the password.
|
||||
*
|
||||
* @param passwordParameter the HTTP parameter to place the password. Default is
|
||||
* "password".
|
||||
* @param password the value of the password parameter. Default is "password".
|
||||
* @return the {@link FormLoginRequestBuilder} for additional customizations
|
||||
*/
|
||||
public FormLoginRequestBuilder password(String passwordParameter,
|
||||
String password) {
|
||||
public FormLoginRequestBuilder password(String passwordParameter, String password) {
|
||||
passwordParam(passwordParameter);
|
||||
this.password = password;
|
||||
return this;
|
||||
@@ -271,7 +268,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specify both the password parameter name and the password.
|
||||
*
|
||||
* @param usernameParameter the HTTP parameter to place the username. Default is
|
||||
* "username".
|
||||
* @param username the value of the username parameter. Default is "user".
|
||||
@@ -285,7 +281,6 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
|
||||
/**
|
||||
* Specify a media type to set as the Accept header in the request.
|
||||
*
|
||||
* @param acceptMediaType the {@link MediaType} to set the Accept header to.
|
||||
* Default is: MediaType.APPLICATION_FORM_URLENCODED
|
||||
* @return the {@link FormLoginRequestBuilder} for additional customizations
|
||||
@@ -305,18 +300,21 @@ public final class SecurityMockMvcRequestBuilders {
|
||||
if (parent == null) {
|
||||
return this;
|
||||
}
|
||||
if (parent instanceof Mergeable ) {
|
||||
if (parent instanceof Mergeable) {
|
||||
this.parent = (Mergeable) parent;
|
||||
return this;
|
||||
} else {
|
||||
}
|
||||
else {
|
||||
throw new IllegalArgumentException("Cannot merge with [" + parent.getClass().getName() + "]");
|
||||
}
|
||||
}
|
||||
|
||||
private FormLoginRequestBuilder() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private SecurityMockMvcRequestBuilders() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+216
-257
File diff suppressed because it is too large
Load Diff
+24
-39
@@ -46,7 +46,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* {@link ResultMatcher} that verifies that a specified user is authenticated.
|
||||
*
|
||||
* @return the {@link AuthenticatedMatcher} to use
|
||||
*/
|
||||
public static AuthenticatedMatcher authenticated() {
|
||||
@@ -55,23 +54,20 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* {@link ResultMatcher} that verifies that no user is authenticated.
|
||||
*
|
||||
* @return the {@link AuthenticatedMatcher} to use
|
||||
*/
|
||||
public static ResultMatcher unauthenticated() {
|
||||
return new UnAuthenticatedMatcher();
|
||||
}
|
||||
|
||||
private static abstract class AuthenticationMatcher<T extends AuthenticationMatcher<T>>
|
||||
implements ResultMatcher {
|
||||
private static abstract class AuthenticationMatcher<T extends AuthenticationMatcher<T>> implements ResultMatcher {
|
||||
|
||||
protected SecurityContext load(MvcResult result) {
|
||||
HttpRequestResponseHolder holder = new HttpRequestResponseHolder(
|
||||
result.getRequest(), result.getResponse());
|
||||
SecurityContextRepository repository = WebTestUtils
|
||||
.getSecurityContextRepository(result.getRequest());
|
||||
HttpRequestResponseHolder holder = new HttpRequestResponseHolder(result.getRequest(), result.getResponse());
|
||||
SecurityContextRepository repository = WebTestUtils.getSecurityContextRepository(result.getRequest());
|
||||
return repository.loadContext(holder);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -81,14 +77,18 @@ public final class SecurityMockMvcResultMatchers {
|
||||
* @author Rob Winch
|
||||
* @since 4.0
|
||||
*/
|
||||
public static final class AuthenticatedMatcher
|
||||
extends AuthenticationMatcher<AuthenticatedMatcher> {
|
||||
public static final class AuthenticatedMatcher extends AuthenticationMatcher<AuthenticatedMatcher> {
|
||||
|
||||
private SecurityContext expectedContext;
|
||||
|
||||
private Authentication expectedAuthentication;
|
||||
|
||||
private Object expectedAuthenticationPrincipal;
|
||||
|
||||
private String expectedAuthenticationName;
|
||||
|
||||
private Collection<? extends GrantedAuthority> expectedGrantedAuthorities;
|
||||
|
||||
private Consumer<Authentication> assertAuthentication;
|
||||
|
||||
@Override
|
||||
@@ -104,25 +104,20 @@ public final class SecurityMockMvcResultMatchers {
|
||||
}
|
||||
|
||||
if (this.expectedContext != null) {
|
||||
assertEquals(this.expectedContext + " does not equal " + context,
|
||||
this.expectedContext, context);
|
||||
assertEquals(this.expectedContext + " does not equal " + context, this.expectedContext, context);
|
||||
}
|
||||
|
||||
if (this.expectedAuthentication != null) {
|
||||
assertEquals(
|
||||
this.expectedAuthentication + " does not equal "
|
||||
+ context.getAuthentication(),
|
||||
assertEquals(this.expectedAuthentication + " does not equal " + context.getAuthentication(),
|
||||
this.expectedAuthentication, context.getAuthentication());
|
||||
}
|
||||
|
||||
if (this.expectedAuthenticationPrincipal != null) {
|
||||
assertTrue("Authentication cannot be null",
|
||||
context.getAuthentication() != null);
|
||||
assertTrue("Authentication cannot be null", context.getAuthentication() != null);
|
||||
assertEquals(
|
||||
this.expectedAuthenticationPrincipal + " does not equal "
|
||||
+ context.getAuthentication().getPrincipal(),
|
||||
this.expectedAuthenticationPrincipal,
|
||||
context.getAuthentication().getPrincipal());
|
||||
this.expectedAuthenticationPrincipal, context.getAuthentication().getPrincipal());
|
||||
}
|
||||
|
||||
if (this.expectedAuthenticationName != null) {
|
||||
@@ -134,14 +129,10 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
if (this.expectedGrantedAuthorities != null) {
|
||||
assertTrue("Authentication cannot be null", auth != null);
|
||||
Collection<? extends GrantedAuthority> authorities = auth
|
||||
.getAuthorities();
|
||||
assertTrue(
|
||||
authorities + " does not contain the same authorities as "
|
||||
+ this.expectedGrantedAuthorities,
|
||||
Collection<? extends GrantedAuthority> authorities = auth.getAuthorities();
|
||||
assertTrue(authorities + " does not contain the same authorities as " + this.expectedGrantedAuthorities,
|
||||
authorities.containsAll(this.expectedGrantedAuthorities));
|
||||
assertTrue(this.expectedGrantedAuthorities
|
||||
+ " does not contain the same authorities as " + authorities,
|
||||
assertTrue(this.expectedGrantedAuthorities + " does not contain the same authorities as " + authorities,
|
||||
this.expectedGrantedAuthorities.containsAll(authorities));
|
||||
}
|
||||
}
|
||||
@@ -158,7 +149,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the expected username
|
||||
*
|
||||
* @param expected the expected username
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -168,7 +158,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the expected {@link SecurityContext}
|
||||
*
|
||||
* @param expected the expected {@link SecurityContext}
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -179,7 +168,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the expected {@link Authentication}
|
||||
*
|
||||
* @param expected the expected {@link Authentication}
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -190,7 +178,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the expected principal
|
||||
*
|
||||
* @param expected the expected principal
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -201,7 +188,6 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the expected {@link Authentication#getName()}
|
||||
*
|
||||
* @param expected the expected {@link Authentication#getName()}
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -212,19 +198,16 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
/**
|
||||
* Specifies the {@link Authentication#getAuthorities()}
|
||||
*
|
||||
* @param expected the {@link Authentication#getAuthorities()}
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
public AuthenticatedMatcher withAuthorities(
|
||||
Collection<? extends GrantedAuthority> expected) {
|
||||
public AuthenticatedMatcher withAuthorities(Collection<? extends GrantedAuthority> expected) {
|
||||
this.expectedGrantedAuthorities = expected;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Specifies the {@link Authentication#getAuthorities()}
|
||||
*
|
||||
* @param roles the roles. Each value is automatically prefixed with "ROLE_"
|
||||
* @return the {@link AuthenticatedMatcher} for further customization
|
||||
*/
|
||||
@@ -238,6 +221,7 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
AuthenticatedMatcher() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -247,8 +231,8 @@ public final class SecurityMockMvcResultMatchers {
|
||||
* @author Rob Winch
|
||||
* @since 4.0
|
||||
*/
|
||||
private static final class UnAuthenticatedMatcher
|
||||
extends AuthenticationMatcher<UnAuthenticatedMatcher> {
|
||||
private static final class UnAuthenticatedMatcher extends AuthenticationMatcher<UnAuthenticatedMatcher> {
|
||||
|
||||
private AuthenticationTrustResolver trustResolver = new AuthenticationTrustResolverImpl();
|
||||
|
||||
@Override
|
||||
@@ -257,14 +241,15 @@ public final class SecurityMockMvcResultMatchers {
|
||||
|
||||
Authentication authentication = context.getAuthentication();
|
||||
assertTrue("Expected anonymous Authentication got " + context,
|
||||
authentication == null
|
||||
|| this.trustResolver.isAnonymous(authentication));
|
||||
authentication == null || this.trustResolver.isAnonymous(authentication));
|
||||
}
|
||||
|
||||
private UnAuthenticatedMatcher() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private SecurityMockMvcResultMatchers() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+19
-19
@@ -41,6 +41,7 @@ import static org.springframework.security.test.web.servlet.request.SecurityMock
|
||||
* @since 4.0
|
||||
*/
|
||||
final class SecurityMockMvcConfigurer extends MockMvcConfigurerAdapter {
|
||||
|
||||
private final DelegateFilter delegateFilter;
|
||||
|
||||
/**
|
||||
@@ -64,25 +65,20 @@ final class SecurityMockMvcConfigurer extends MockMvcConfigurerAdapter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public RequestPostProcessor beforeMockMvcCreated(
|
||||
ConfigurableMockMvcBuilder<?> builder, WebApplicationContext context) {
|
||||
public RequestPostProcessor beforeMockMvcCreated(ConfigurableMockMvcBuilder<?> builder,
|
||||
WebApplicationContext context) {
|
||||
String securityBeanId = BeanIds.SPRING_SECURITY_FILTER_CHAIN;
|
||||
if (getSpringSecurityFilterChain() == null
|
||||
&& context.containsBean(securityBeanId)) {
|
||||
setSpringSecurityFitlerChain(context.getBean(securityBeanId,
|
||||
Filter.class));
|
||||
if (getSpringSecurityFilterChain() == null && context.containsBean(securityBeanId)) {
|
||||
setSpringSecurityFitlerChain(context.getBean(securityBeanId, Filter.class));
|
||||
}
|
||||
|
||||
if (getSpringSecurityFilterChain() == null) {
|
||||
throw new IllegalStateException(
|
||||
"springSecurityFilterChain cannot be null. Ensure a Bean with the name "
|
||||
+ securityBeanId
|
||||
+ " implementing Filter is present or inject the Filter to be used.");
|
||||
throw new IllegalStateException("springSecurityFilterChain cannot be null. Ensure a Bean with the name "
|
||||
+ securityBeanId + " implementing Filter is present or inject the Filter to be used.");
|
||||
}
|
||||
|
||||
// This is used by other test support to obtain the FilterChainProxy
|
||||
context.getServletContext().setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN,
|
||||
getSpringSecurityFilterChain());
|
||||
context.getServletContext().setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN, getSpringSecurityFilterChain());
|
||||
|
||||
return testSecurityContext();
|
||||
}
|
||||
@@ -96,11 +92,13 @@ final class SecurityMockMvcConfigurer extends MockMvcConfigurerAdapter {
|
||||
}
|
||||
|
||||
/**
|
||||
* Allows adding in {@link #afterConfigurerAdded(ConfigurableMockMvcBuilder)} to preserve Filter order and then
|
||||
* lazily set the delegate in {@link #beforeMockMvcCreated(ConfigurableMockMvcBuilder, WebApplicationContext)}.
|
||||
* Allows adding in {@link #afterConfigurerAdded(ConfigurableMockMvcBuilder)} to
|
||||
* preserve Filter order and then lazily set the delegate in
|
||||
* {@link #beforeMockMvcCreated(ConfigurableMockMvcBuilder, WebApplicationContext)}.
|
||||
*
|
||||
* {@link org.springframework.web.filter.DelegatingFilterProxy} is not used because it is not easy to lazily set
|
||||
* the delegate or get the delegate which is necessary for the test infrastructure.
|
||||
* {@link org.springframework.web.filter.DelegatingFilterProxy} is not used because it
|
||||
* is not easy to lazily set the delegate or get the delegate which is necessary for
|
||||
* the test infrastructure.
|
||||
*/
|
||||
static class DelegateFilter implements Filter {
|
||||
|
||||
@@ -120,9 +118,9 @@ final class SecurityMockMvcConfigurer extends MockMvcConfigurerAdapter {
|
||||
Filter getDelegate() {
|
||||
Filter result = this.delegate;
|
||||
if (result == null) {
|
||||
throw new IllegalStateException("delegate cannot be null. Ensure a Bean with the name "
|
||||
+ BeanIds.SPRING_SECURITY_FILTER_CHAIN
|
||||
+ " implementing Filter is present or inject the Filter to be used.");
|
||||
throw new IllegalStateException(
|
||||
"delegate cannot be null. Ensure a Bean with the name " + BeanIds.SPRING_SECURITY_FILTER_CHAIN
|
||||
+ " implementing Filter is present or inject the Filter to be used.");
|
||||
}
|
||||
return result;
|
||||
}
|
||||
@@ -157,5 +155,7 @@ final class SecurityMockMvcConfigurer extends MockMvcConfigurerAdapter {
|
||||
public String toString() {
|
||||
return getDelegate().toString();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+3
-5
@@ -28,6 +28,7 @@ import javax.servlet.Filter;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public final class SecurityMockMvcConfigurers {
|
||||
|
||||
/**
|
||||
* Configures the MockMvcBuilder for use with Spring Security. Specifically the
|
||||
* configurer adds the Spring Bean named "springSecurityFilterChain" as a Filter. It
|
||||
@@ -35,7 +36,6 @@ public final class SecurityMockMvcConfigurers {
|
||||
* by applying
|
||||
* {@link org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors#testSecurityContext()}
|
||||
* .
|
||||
*
|
||||
* @return the {@link org.springframework.test.web.servlet.setup.MockMvcConfigurer} to
|
||||
* use
|
||||
*/
|
||||
@@ -49,15 +49,13 @@ public final class SecurityMockMvcConfigurers {
|
||||
* TestSecurityContextHolder is leveraged for each request by applying
|
||||
* {@link org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors#testSecurityContext()}
|
||||
* .
|
||||
*
|
||||
* @param springSecurityFilterChain the Filter to be added
|
||||
*
|
||||
* @return the {@link org.springframework.test.web.servlet.setup.MockMvcConfigurer} to
|
||||
* use
|
||||
*/
|
||||
public static MockMvcConfigurer springSecurity(Filter springSecurityFilterChain) {
|
||||
Assert.notNull(springSecurityFilterChain,
|
||||
"springSecurityFilterChain cannot be null");
|
||||
Assert.notNull(springSecurityFilterChain, "springSecurityFilterChain cannot be null");
|
||||
return new SecurityMockMvcConfigurer(springSecurityFilterChain);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+12
-22
@@ -41,23 +41,22 @@ import org.springframework.web.context.support.WebApplicationContextUtils;
|
||||
* @since 4.0
|
||||
*/
|
||||
public abstract class WebTestUtils {
|
||||
|
||||
private static final SecurityContextRepository DEFAULT_CONTEXT_REPO = new HttpSessionSecurityContextRepository();
|
||||
|
||||
private static final CsrfTokenRepository DEFAULT_TOKEN_REPO = new HttpSessionCsrfTokenRepository();
|
||||
|
||||
/**
|
||||
* Gets the {@link SecurityContextRepository} for the specified
|
||||
* {@link HttpServletRequest}. If one is not found, a default
|
||||
* {@link HttpSessionSecurityContextRepository} is used.
|
||||
*
|
||||
* @param request the {@link HttpServletRequest} to obtain the
|
||||
* {@link SecurityContextRepository}
|
||||
* @return the {@link SecurityContextRepository} for the specified
|
||||
* {@link HttpServletRequest}
|
||||
*/
|
||||
public static SecurityContextRepository getSecurityContextRepository(
|
||||
HttpServletRequest request) {
|
||||
SecurityContextPersistenceFilter filter = findFilter(request,
|
||||
SecurityContextPersistenceFilter.class);
|
||||
public static SecurityContextRepository getSecurityContextRepository(HttpServletRequest request) {
|
||||
SecurityContextPersistenceFilter filter = findFilter(request, SecurityContextPersistenceFilter.class);
|
||||
if (filter == null) {
|
||||
return DEFAULT_CONTEXT_REPO;
|
||||
}
|
||||
@@ -67,15 +66,13 @@ public abstract class WebTestUtils {
|
||||
/**
|
||||
* Sets the {@link SecurityContextRepository} for the specified
|
||||
* {@link HttpServletRequest}.
|
||||
*
|
||||
* @param request the {@link HttpServletRequest} to obtain the
|
||||
* {@link SecurityContextRepository}
|
||||
* @param securityContextRepository the {@link SecurityContextRepository} to set
|
||||
*/
|
||||
public static void setSecurityContextRepository(HttpServletRequest request,
|
||||
SecurityContextRepository securityContextRepository) {
|
||||
SecurityContextPersistenceFilter filter = findFilter(request,
|
||||
SecurityContextPersistenceFilter.class);
|
||||
SecurityContextPersistenceFilter filter = findFilter(request, SecurityContextPersistenceFilter.class);
|
||||
if (filter != null) {
|
||||
ReflectionTestUtils.setField(filter, "repo", securityContextRepository);
|
||||
}
|
||||
@@ -84,7 +81,6 @@ public abstract class WebTestUtils {
|
||||
/**
|
||||
* Gets the {@link CsrfTokenRepository} for the specified {@link HttpServletRequest}.
|
||||
* If one is not found, the default {@link HttpSessionCsrfTokenRepository} is used.
|
||||
*
|
||||
* @param request the {@link HttpServletRequest} to obtain the
|
||||
* {@link CsrfTokenRepository}
|
||||
* @return the {@link CsrfTokenRepository} for the specified
|
||||
@@ -95,19 +91,16 @@ public abstract class WebTestUtils {
|
||||
if (filter == null) {
|
||||
return DEFAULT_TOKEN_REPO;
|
||||
}
|
||||
return (CsrfTokenRepository) ReflectionTestUtils.getField(filter,
|
||||
"tokenRepository");
|
||||
return (CsrfTokenRepository) ReflectionTestUtils.getField(filter, "tokenRepository");
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the {@link CsrfTokenRepository} for the specified {@link HttpServletRequest}.
|
||||
*
|
||||
* @param request the {@link HttpServletRequest} to obtain the
|
||||
* {@link CsrfTokenRepository}
|
||||
* @param repository the {@link CsrfTokenRepository} to set
|
||||
*/
|
||||
public static void setCsrfTokenRepository(HttpServletRequest request,
|
||||
CsrfTokenRepository repository) {
|
||||
public static void setCsrfTokenRepository(HttpServletRequest request, CsrfTokenRepository repository) {
|
||||
CsrfFilter filter = findFilter(request, CsrfFilter.class);
|
||||
if (filter != null) {
|
||||
ReflectionTestUtils.setField(filter, "tokenRepository", repository);
|
||||
@@ -115,15 +108,13 @@ public abstract class WebTestUtils {
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
static <T extends Filter> T findFilter(HttpServletRequest request,
|
||||
Class<T> filterClass) {
|
||||
static <T extends Filter> T findFilter(HttpServletRequest request, Class<T> filterClass) {
|
||||
ServletContext servletContext = request.getServletContext();
|
||||
Filter springSecurityFilterChain = getSpringSecurityFilterChain(servletContext);
|
||||
if (springSecurityFilterChain == null) {
|
||||
return null;
|
||||
}
|
||||
List<Filter> filters = ReflectionTestUtils
|
||||
.invokeMethod(springSecurityFilterChain, "getFilters", request);
|
||||
List<Filter> filters = ReflectionTestUtils.invokeMethod(springSecurityFilterChain, "getFilters", request);
|
||||
if (filters == null) {
|
||||
return null;
|
||||
}
|
||||
@@ -136,8 +127,7 @@ public abstract class WebTestUtils {
|
||||
}
|
||||
|
||||
private static Filter getSpringSecurityFilterChain(ServletContext servletContext) {
|
||||
Filter result = (Filter) servletContext
|
||||
.getAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN);
|
||||
Filter result = (Filter) servletContext.getAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN);
|
||||
if (result != null) {
|
||||
return result;
|
||||
}
|
||||
@@ -145,8 +135,7 @@ public abstract class WebTestUtils {
|
||||
.getWebApplicationContext(servletContext);
|
||||
if (webApplicationContext != null) {
|
||||
try {
|
||||
return webApplicationContext.getBean(
|
||||
AbstractSecurityWebApplicationInitializer.DEFAULT_FILTER_NAME,
|
||||
return webApplicationContext.getBean(AbstractSecurityWebApplicationInitializer.DEFAULT_FILTER_NAME,
|
||||
Filter.class);
|
||||
}
|
||||
catch (NoSuchBeanDefinitionException notFound) {
|
||||
@@ -157,4 +146,5 @@ public abstract class WebTestUtils {
|
||||
|
||||
private WebTestUtils() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
@@ -72,4 +72,5 @@ public class TestSecurityContextHolderTests {
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication()).isSameAs(authentication);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
-7
@@ -39,16 +39,13 @@ public class SecurityTestExecutionListenerTests {
|
||||
assertThat(SecurityContextHolder.getContext().getAuthentication().getName()).isEqualTo("user");
|
||||
}
|
||||
|
||||
|
||||
@WithMockUser
|
||||
@Test
|
||||
public void reactorContextTestSecurityContextHolderExecutionListenerTestIsRegistered() {
|
||||
Mono<String> name = ReactiveSecurityContextHolder.getContext()
|
||||
.map(SecurityContext::getAuthentication)
|
||||
.map(Principal::getName);
|
||||
Mono<String> name = ReactiveSecurityContextHolder.getContext().map(SecurityContext::getAuthentication)
|
||||
.map(Principal::getName);
|
||||
|
||||
StepVerifier.create(name)
|
||||
.expectNext("user")
|
||||
.verifyComplete();
|
||||
StepVerifier.create(name).expectNext("user").verifyComplete();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
@@ -25,8 +25,11 @@ import java.util.Collection;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class CustomUserDetails implements UserDetails {
|
||||
|
||||
private final String name;
|
||||
|
||||
private final String username;
|
||||
|
||||
private final Collection<? extends GrantedAuthority> authorities;
|
||||
|
||||
public CustomUserDetails(String name, String username) {
|
||||
@@ -67,4 +70,5 @@ public class CustomUserDetails implements UserDetails {
|
||||
public String toString() {
|
||||
return "CustomUserDetails{" + "username='" + username + '\'' + '}';
|
||||
}
|
||||
|
||||
}
|
||||
+2
-1
@@ -22,6 +22,7 @@ import org.springframework.security.test.context.support.WithSecurityContext;
|
||||
*/
|
||||
@WithSecurityContext(factory = WithMockCustomUserSecurityContextFactory.class)
|
||||
public @interface WithMockCustomUser {
|
||||
|
||||
/**
|
||||
* The username to be used. The default is rob
|
||||
* @return
|
||||
@@ -33,7 +34,6 @@ public @interface WithMockCustomUser {
|
||||
* {@link org.springframework.security.core.GrantedAuthority} will be created for each
|
||||
* value within roles. Each value in roles will automatically be prefixed with
|
||||
* "ROLE_". For example, the default will result in "ROLE_USER" being used.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String[] roles() default { "USER" };
|
||||
@@ -43,4 +43,5 @@ public @interface WithMockCustomUser {
|
||||
* @return
|
||||
*/
|
||||
String name() default "Rob Winch";
|
||||
|
||||
}
|
||||
|
||||
+6
-6
@@ -24,16 +24,16 @@ import org.springframework.security.test.context.support.WithSecurityContextFact
|
||||
/**
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public class WithMockCustomUserSecurityContextFactory implements
|
||||
WithSecurityContextFactory<WithMockCustomUser> {
|
||||
public class WithMockCustomUserSecurityContextFactory implements WithSecurityContextFactory<WithMockCustomUser> {
|
||||
|
||||
public SecurityContext createSecurityContext(WithMockCustomUser customUser) {
|
||||
SecurityContext context = SecurityContextHolder.createEmptyContext();
|
||||
|
||||
CustomUserDetails principal = new CustomUserDetails(customUser.name(),
|
||||
customUser.username());
|
||||
Authentication auth = new UsernamePasswordAuthenticationToken(principal,
|
||||
"password", principal.getAuthorities());
|
||||
CustomUserDetails principal = new CustomUserDetails(customUser.name(), customUser.username());
|
||||
Authentication auth = new UsernamePasswordAuthenticationToken(principal, "password",
|
||||
principal.getAuthorities());
|
||||
context.setAuthentication(auth);
|
||||
return context;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+3
@@ -48,6 +48,7 @@ public class WithMockUserParentTests extends WithMockUserParent {
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@ComponentScan(basePackageClasses = HelloMessageService.class)
|
||||
static class Config {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -56,5 +57,7 @@ public class WithMockUserParentTests extends WithMockUserParent {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+5
-2
@@ -37,6 +37,7 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@ContextConfiguration(classes = WithMockUserTests.Config.class)
|
||||
public class WithMockUserTests {
|
||||
|
||||
@Autowired
|
||||
private MessageService messageService;
|
||||
|
||||
@@ -63,8 +64,7 @@ public class WithMockUserTests {
|
||||
@WithMockUser(username = "admin", roles = { "USER", "ADMIN" })
|
||||
public void getMessageWithMockUserCustomUser() {
|
||||
String message = messageService.getMessage();
|
||||
assertThat(message).contains("admin").contains("ROLE_USER")
|
||||
.contains("ROLE_ADMIN");
|
||||
assertThat(message).contains("admin").contains("ROLE_USER").contains("ROLE_ADMIN");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -77,6 +77,7 @@ public class WithMockUserTests {
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@ComponentScan(basePackageClasses = HelloMessageService.class)
|
||||
static class Config {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -85,5 +86,7 @@ public class WithMockUserTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+7
-3
@@ -42,6 +42,7 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@ContextConfiguration(classes = WithUserDetailsTests.Config.class)
|
||||
public class WithUserDetailsTests {
|
||||
|
||||
@Autowired
|
||||
private MessageService messageService;
|
||||
|
||||
@@ -67,7 +68,7 @@ public class WithUserDetailsTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
@WithUserDetails(value="customUsername", userDetailsServiceBeanName="myUserDetailsService")
|
||||
@WithUserDetails(value = "customUsername", userDetailsServiceBeanName = "myUserDetailsService")
|
||||
public void getMessageWithUserDetailsServiceBeanName() {
|
||||
String message = messageService.getMessage();
|
||||
assertThat(message).contains("customUsername");
|
||||
@@ -77,6 +78,7 @@ public class WithUserDetailsTests {
|
||||
@EnableGlobalMethodSecurity(prePostEnabled = true)
|
||||
@ComponentScan(basePackageClasses = HelloMessageService.class)
|
||||
static class Config {
|
||||
|
||||
@Autowired
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -89,6 +91,7 @@ public class WithUserDetailsTests {
|
||||
public UserDetailsService myUserDetailsService() {
|
||||
return new CustomUserDetailsService();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private Object getPrincipal() {
|
||||
@@ -97,9 +100,10 @@ public class WithUserDetailsTests {
|
||||
|
||||
static class CustomUserDetailsService implements UserDetailsService {
|
||||
|
||||
public UserDetails loadUserByUsername(final String username)
|
||||
throws UsernameNotFoundException {
|
||||
public UserDetails loadUserByUsername(final String username) throws UsernameNotFoundException {
|
||||
return new CustomUserDetails("name", username);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+2
-2
@@ -28,8 +28,8 @@ public class HelloMessageService implements MessageService {
|
||||
|
||||
@PreAuthorize("authenticated")
|
||||
public String getMessage() {
|
||||
Authentication authentication = SecurityContextHolder.getContext()
|
||||
.getAuthentication();
|
||||
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
|
||||
return "Hello " + authentication;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+2
@@ -19,5 +19,7 @@ package org.springframework.security.test.context.showcase.service;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
public interface MessageService {
|
||||
|
||||
String getMessage();
|
||||
|
||||
}
|
||||
|
||||
+36
-43
@@ -49,8 +49,7 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
@Mock
|
||||
private TestContext testContext;
|
||||
|
||||
private ReactorContextTestExecutionListener listener =
|
||||
new ReactorContextTestExecutionListener();
|
||||
private ReactorContextTestExecutionListener listener = new ReactorContextTestExecutionListener();
|
||||
|
||||
@After
|
||||
public void cleanup() {
|
||||
@@ -62,11 +61,9 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
public void beforeTestMethodWhenSecurityContextEmptyThenReactorContextNull() throws Exception {
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
Mono<?> result = ReactiveSecurityContextHolder
|
||||
.getContext();
|
||||
Mono<?> result = ReactiveSecurityContextHolder.getContext();
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(result).verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -75,16 +72,15 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
Mono<?> result = ReactiveSecurityContextHolder
|
||||
.getContext();
|
||||
Mono<?> result = ReactiveSecurityContextHolder.getContext();
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(result).verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beforeTestMethodWhenAuthenticationThenReactorContextHasAuthentication() throws Exception {
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password", "ROLE_USER");
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password",
|
||||
"ROLE_USER");
|
||||
TestSecurityContextHolder.setAuthentication(expectedAuthentication);
|
||||
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
@@ -94,7 +90,8 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
|
||||
@Test
|
||||
public void beforeTestMethodWhenCustomContext() throws Exception {
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password", "ROLE_USER");
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password",
|
||||
"ROLE_USER");
|
||||
SecurityContext context = new CustomContext(expectedAuthentication);
|
||||
TestSecurityContextHolder.setContext(context);
|
||||
|
||||
@@ -104,6 +101,7 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
}
|
||||
|
||||
static class CustomContext implements SecurityContext {
|
||||
|
||||
private Authentication authentication;
|
||||
|
||||
CustomContext(Authentication authentication) {
|
||||
@@ -119,43 +117,42 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
public void setAuthentication(Authentication authentication) {
|
||||
this.authentication = authentication;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beforeTestMethodWhenExistingAuthenticationThenReactorContextHasOriginalAuthentication() throws Exception {
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password", "ROLE_USER");
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password", "ROLE_USER");
|
||||
public void beforeTestMethodWhenExistingAuthenticationThenReactorContextHasOriginalAuthentication()
|
||||
throws Exception {
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password",
|
||||
"ROLE_USER");
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password",
|
||||
"ROLE_USER");
|
||||
TestSecurityContextHolder.setAuthentication(contextHolder);
|
||||
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
Mono<Authentication> authentication = Mono.just("any")
|
||||
.flatMap(s -> ReactiveSecurityContextHolder.getContext()
|
||||
.map(SecurityContext::getAuthentication)
|
||||
)
|
||||
.subscriberContext(ReactiveSecurityContextHolder.withAuthentication(expectedAuthentication));
|
||||
.flatMap(s -> ReactiveSecurityContextHolder.getContext().map(SecurityContext::getAuthentication))
|
||||
.subscriberContext(ReactiveSecurityContextHolder.withAuthentication(expectedAuthentication));
|
||||
|
||||
StepVerifier.create(authentication)
|
||||
.expectNext(expectedAuthentication)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(authentication).expectNext(expectedAuthentication).verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beforeTestMethodWhenClearThenReactorContextDoesNotOverride() throws Exception {
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password", "ROLE_USER");
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password", "ROLE_USER");
|
||||
TestingAuthenticationToken expectedAuthentication = new TestingAuthenticationToken("user", "password",
|
||||
"ROLE_USER");
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password",
|
||||
"ROLE_USER");
|
||||
TestSecurityContextHolder.setAuthentication(contextHolder);
|
||||
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
Mono<Authentication> authentication = Mono.just("any")
|
||||
.flatMap(s -> ReactiveSecurityContextHolder.getContext()
|
||||
.map(SecurityContext::getAuthentication)
|
||||
)
|
||||
.subscriberContext(ReactiveSecurityContextHolder.clearContext());
|
||||
.flatMap(s -> ReactiveSecurityContextHolder.getContext().map(SecurityContext::getAuthentication))
|
||||
.subscriberContext(ReactiveSecurityContextHolder.clearContext());
|
||||
|
||||
StepVerifier.create(authentication)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(authentication).verifyComplete();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -194,32 +191,28 @@ public class ReactorContextTestExecutionListenerTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void checkSecurityContextResolutionWhenSubscribedContextCalledOnTheDifferentThreadThanWithSecurityContextTestExecutionListener() throws Exception {
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password", "ROLE_USER");
|
||||
public void checkSecurityContextResolutionWhenSubscribedContextCalledOnTheDifferentThreadThanWithSecurityContextTestExecutionListener()
|
||||
throws Exception {
|
||||
TestingAuthenticationToken contextHolder = new TestingAuthenticationToken("contextHolder", "password",
|
||||
"ROLE_USER");
|
||||
TestSecurityContextHolder.setAuthentication(contextHolder);
|
||||
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
ForkJoinPool.commonPool()
|
||||
.submit(() -> assertAuthentication(contextHolder))
|
||||
.join();
|
||||
ForkJoinPool.commonPool().submit(() -> assertAuthentication(contextHolder)).join();
|
||||
}
|
||||
|
||||
public void assertAuthentication(Authentication expected) {
|
||||
Mono<Authentication> authentication = ReactiveSecurityContextHolder.getContext()
|
||||
.map(SecurityContext::getAuthentication);
|
||||
.map(SecurityContext::getAuthentication);
|
||||
|
||||
StepVerifier.create(authentication)
|
||||
.expectNext(expected)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(authentication).expectNext(expected).verifyComplete();
|
||||
}
|
||||
|
||||
|
||||
private void assertSecurityContext(SecurityContext expected) {
|
||||
Mono<SecurityContext> securityContext = ReactiveSecurityContextHolder.getContext();
|
||||
|
||||
StepVerifier.create(securityContext)
|
||||
.expectNext(expected)
|
||||
.verifyComplete();
|
||||
StepVerifier.create(securityContext).expectNext(expected).verifyComplete();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+8
-4
@@ -26,22 +26,23 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
* @since 5.0
|
||||
*/
|
||||
public class WithAnonymousUserTests {
|
||||
|
||||
@Test
|
||||
public void defaults() {
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(Annotated.class,
|
||||
WithSecurityContext.class);
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
}
|
||||
|
||||
@WithAnonymousUser
|
||||
private class Annotated {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupExplicitThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils
|
||||
.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
@@ -49,17 +50,20 @@ public class WithAnonymousUserTests {
|
||||
|
||||
@WithAnonymousUser(setupBefore = TestExecutionEvent.TEST_METHOD)
|
||||
private class SetupExplicit {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupOverriddenThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupOverridden.class,
|
||||
WithSecurityContext.class);
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_EXECUTION);
|
||||
}
|
||||
|
||||
@WithAnonymousUser(setupBefore = TestExecutionEvent.TEST_EXECUTION)
|
||||
private class SetupOverridden {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+6
-10
@@ -49,8 +49,7 @@ public class WithMockUserSecurityContextFactoryTests {
|
||||
when(withUser.roles()).thenReturn(new String[] { "USER" });
|
||||
when(withUser.authorities()).thenReturn(new String[] {});
|
||||
|
||||
assertThat(factory.createSecurityContext(withUser).getAuthentication().getName())
|
||||
.isEqualTo(withUser.value());
|
||||
assertThat(factory.createSecurityContext(withUser).getAuthentication().getName()).isEqualTo(withUser.value());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -71,10 +70,8 @@ public class WithMockUserSecurityContextFactoryTests {
|
||||
when(withUser.roles()).thenReturn(new String[] { "USER", "CUSTOM" });
|
||||
when(withUser.authorities()).thenReturn(new String[] {});
|
||||
|
||||
assertThat(
|
||||
factory.createSecurityContext(withUser).getAuthentication()
|
||||
.getAuthorities()).extracting("authority").containsOnly(
|
||||
"ROLE_USER", "ROLE_CUSTOM");
|
||||
assertThat(factory.createSecurityContext(withUser).getAuthentication().getAuthorities()).extracting("authority")
|
||||
.containsOnly("ROLE_USER", "ROLE_CUSTOM");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -84,10 +81,8 @@ public class WithMockUserSecurityContextFactoryTests {
|
||||
when(withUser.roles()).thenReturn(new String[] { "USER" });
|
||||
when(withUser.authorities()).thenReturn(new String[] { "USER", "CUSTOM" });
|
||||
|
||||
assertThat(
|
||||
factory.createSecurityContext(withUser).getAuthentication()
|
||||
.getAuthorities()).extracting("authority").containsOnly(
|
||||
"USER", "CUSTOM");
|
||||
assertThat(factory.createSecurityContext(withUser).getAuthentication().getAuthorities()).extracting("authority")
|
||||
.containsOnly("USER", "CUSTOM");
|
||||
}
|
||||
|
||||
@Test(expected = IllegalStateException.class)
|
||||
@@ -107,4 +102,5 @@ public class WithMockUserSecurityContextFactoryTests {
|
||||
|
||||
factory.createSecurityContext(withUser);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+8
-6
@@ -25,8 +25,7 @@ public class WithMockUserTests {
|
||||
|
||||
@Test
|
||||
public void defaults() {
|
||||
WithMockUser mockUser = AnnotatedElementUtils.findMergedAnnotation(Annotated.class,
|
||||
WithMockUser.class);
|
||||
WithMockUser mockUser = AnnotatedElementUtils.findMergedAnnotation(Annotated.class, WithMockUser.class);
|
||||
assertThat(mockUser.value()).isEqualTo("user");
|
||||
assertThat(mockUser.username()).isEmpty();
|
||||
assertThat(mockUser.password()).isEqualTo("password");
|
||||
@@ -34,19 +33,19 @@ public class WithMockUserTests {
|
||||
assertThat(mockUser.setupBefore()).isEqualByComparingTo(TestExecutionEvent.TEST_METHOD);
|
||||
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(Annotated.class,
|
||||
WithSecurityContext.class);
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
}
|
||||
|
||||
@WithMockUser
|
||||
private class Annotated {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupExplicitThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils
|
||||
.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
@@ -54,17 +53,20 @@ public class WithMockUserTests {
|
||||
|
||||
@WithMockUser(setupBefore = TestExecutionEvent.TEST_METHOD)
|
||||
private class SetupExplicit {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupOverriddenThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupOverridden.class,
|
||||
WithSecurityContext.class);
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_EXECUTION);
|
||||
}
|
||||
|
||||
@WithMockUser(setupBefore = TestExecutionEvent.TEST_EXECUTION)
|
||||
private class SetupOverridden {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+15
-12
@@ -50,6 +50,7 @@ import static org.mockito.Mockito.when;
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class WithSecurityContextTestExcecutionListenerTests {
|
||||
|
||||
private ConfigurableApplicationContext context;
|
||||
|
||||
@Mock
|
||||
@@ -76,8 +77,7 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
public void beforeTestMethodNullSecurityContextNoError() throws Exception {
|
||||
Class testClass = FakeTest.class;
|
||||
when(testContext.getTestClass()).thenReturn(testClass);
|
||||
when(testContext.getTestMethod()).thenReturn(
|
||||
ReflectionUtils.findMethod(testClass, "testNoAnnotation"));
|
||||
when(testContext.getTestMethod()).thenReturn(ReflectionUtils.findMethod(testClass, "testNoAnnotation"));
|
||||
|
||||
listener.beforeTestMethod(testContext);
|
||||
}
|
||||
@@ -87,14 +87,13 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
public void beforeTestMethodNoApplicationContext() throws Exception {
|
||||
Class testClass = FakeTest.class;
|
||||
when(testContext.getApplicationContext()).thenThrow(new IllegalStateException());
|
||||
when(testContext.getTestMethod()).thenReturn(
|
||||
ReflectionUtils.findMethod(testClass, "testWithMockUser"));
|
||||
when(testContext.getTestMethod()).thenReturn(ReflectionUtils.findMethod(testClass, "testWithMockUser"));
|
||||
|
||||
listener.beforeTestMethod(testContext);
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication().getName())
|
||||
.isEqualTo("user");
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication().getName()).isEqualTo("user");
|
||||
}
|
||||
|
||||
// gh-3962
|
||||
@Test
|
||||
public void withSecurityContextAfterSqlScripts() {
|
||||
@@ -126,13 +125,11 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
@Test
|
||||
// gh-3837
|
||||
public void handlesGenericAnnotation() throws Exception {
|
||||
Method method = ReflectionUtils.findMethod(
|
||||
WithSecurityContextTestExcecutionListenerTests.class,
|
||||
Method method = ReflectionUtils.findMethod(WithSecurityContextTestExcecutionListenerTests.class,
|
||||
"handlesGenericAnnotationTestMethod");
|
||||
TestContext testContext = mock(TestContext.class);
|
||||
when(testContext.getTestMethod()).thenReturn(method);
|
||||
when(testContext.getApplicationContext())
|
||||
.thenThrow(new IllegalStateException(""));
|
||||
when(testContext.getApplicationContext()).thenThrow(new IllegalStateException(""));
|
||||
|
||||
this.listener.beforeTestMethod(testContext);
|
||||
|
||||
@@ -147,11 +144,12 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@WithSecurityContext(factory = SuperClassWithSecurityContextFactory.class)
|
||||
@interface WithSuperClassWithSecurityContext {
|
||||
|
||||
String username() default "WithSuperClassWithSecurityContext";
|
||||
|
||||
}
|
||||
|
||||
static class SuperClassWithSecurityContextFactory
|
||||
implements WithSecurityContextFactory<Annotation> {
|
||||
static class SuperClassWithSecurityContextFactory implements WithSecurityContextFactory<Annotation> {
|
||||
|
||||
@Override
|
||||
public SecurityContext createSecurityContext(Annotation annotation) {
|
||||
@@ -159,9 +157,11 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
context.setAuthentication(new TestingAuthenticationToken(annotation, "NA"));
|
||||
return context;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class FakeTest {
|
||||
|
||||
public void testNoAnnotation() {
|
||||
}
|
||||
|
||||
@@ -169,9 +169,12 @@ public class WithSecurityContextTestExcecutionListenerTests {
|
||||
public void testWithMockUser() {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class Config {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+17
-7
@@ -54,8 +54,10 @@ import static org.mockito.Mockito.when;
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
@ContextConfiguration(classes = WithSecurityContextTestExecutionListenerTests.NoOpConfiguration.class)
|
||||
public class WithSecurityContextTestExecutionListenerTests {
|
||||
|
||||
@ClassRule
|
||||
public static final SpringClassRule spring = new SpringClassRule();
|
||||
|
||||
@Rule
|
||||
public final SpringMethodRule springMethod = new SpringMethodRule();
|
||||
|
||||
@@ -81,7 +83,8 @@ public class WithSecurityContextTestExecutionListenerTests {
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication()).isNotNull();
|
||||
verify(this.testContext, never()).setAttribute(eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME), any(SecurityContext.class));
|
||||
verify(this.testContext, never()).setAttribute(
|
||||
eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME), any(SecurityContext.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -93,7 +96,8 @@ public class WithSecurityContextTestExecutionListenerTests {
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication()).isNotNull();
|
||||
verify(this.testContext, never()).setAttribute(eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME), any(SecurityContext.class));
|
||||
verify(this.testContext, never()).setAttribute(
|
||||
eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME), any(SecurityContext.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -105,8 +109,8 @@ public class WithSecurityContextTestExecutionListenerTests {
|
||||
this.listener.beforeTestMethod(this.testContext);
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication()).isNull();
|
||||
verify(this.testContext).setAttribute(eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME)
|
||||
, ArgumentMatchers.<Supplier<SecurityContext>>any());
|
||||
verify(this.testContext).setAttribute(eq(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME),
|
||||
ArgumentMatchers.<Supplier<SecurityContext>>any());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -148,17 +152,22 @@ public class WithSecurityContextTestExecutionListenerTests {
|
||||
SecurityContextImpl securityContext = new SecurityContextImpl();
|
||||
securityContext.setAuthentication(new TestingAuthenticationToken("user", "passsword", "ROLE_USER"));
|
||||
Supplier<SecurityContext> supplier = () -> securityContext;
|
||||
when(this.testContext.removeAttribute(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME)).thenReturn(supplier);
|
||||
when(this.testContext.removeAttribute(WithSecurityContextTestExecutionListener.SECURITY_CONTEXT_ATTR_NAME))
|
||||
.thenReturn(supplier);
|
||||
|
||||
this.listener.beforeTestExecution(this.testContext);
|
||||
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication()).isEqualTo(securityContext.getAuthentication());
|
||||
assertThat(TestSecurityContextHolder.getContext().getAuthentication())
|
||||
.isEqualTo(securityContext.getAuthentication());
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class NoOpConfiguration {}
|
||||
static class NoOpConfiguration {
|
||||
|
||||
}
|
||||
|
||||
static class TheTest {
|
||||
|
||||
@WithMockUser(setupBefore = TestExecutionEvent.TEST_EXECUTION)
|
||||
public void withMockUserTestExecution() {
|
||||
}
|
||||
@@ -174,6 +183,7 @@ public class WithSecurityContextTestExecutionListenerTests {
|
||||
@WithUserDetails(setupBefore = TestExecutionEvent.TEST_EXECUTION)
|
||||
public void withUserDetails() {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+12
-10
@@ -40,10 +40,13 @@ public class WithUserDetailsSecurityContextFactoryTests {
|
||||
|
||||
@Mock
|
||||
private ReactiveUserDetailsService reactiveUserDetailsService;
|
||||
|
||||
@Mock
|
||||
private UserDetailsService userDetailsService;
|
||||
|
||||
@Mock
|
||||
private UserDetails userDetails;
|
||||
|
||||
@Mock
|
||||
private BeanFactory beans;
|
||||
|
||||
@@ -78,8 +81,7 @@ public class WithUserDetailsSecurityContextFactoryTests {
|
||||
when(userDetailsService.loadUserByUsername(username)).thenReturn(userDetails);
|
||||
|
||||
SecurityContext context = factory.createSecurityContext(withUserDetails);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getPrincipal()).isEqualTo(userDetails);
|
||||
verify(beans).getBean(UserDetailsService.class);
|
||||
}
|
||||
@@ -89,15 +91,15 @@ public class WithUserDetailsSecurityContextFactoryTests {
|
||||
public void createSecurityContextWithUserDetailsServiceName() {
|
||||
String beanName = "secondUserDetailsServiceBean";
|
||||
String username = "user";
|
||||
when(this.beans.getBean(beanName, ReactiveUserDetailsService.class)).thenThrow(new BeanNotOfRequiredTypeException("", ReactiveUserDetailsService.class, UserDetailsService.class));
|
||||
when(this.beans.getBean(beanName, ReactiveUserDetailsService.class)).thenThrow(
|
||||
new BeanNotOfRequiredTypeException("", ReactiveUserDetailsService.class, UserDetailsService.class));
|
||||
when(withUserDetails.value()).thenReturn(username);
|
||||
when(withUserDetails.userDetailsServiceBeanName()).thenReturn(beanName);
|
||||
when(userDetailsService.loadUserByUsername(username)).thenReturn(userDetails);
|
||||
when(beans.getBean(beanName, UserDetailsService.class)).thenReturn(userDetailsService);
|
||||
|
||||
SecurityContext context = factory.createSecurityContext(withUserDetails);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getPrincipal()).isEqualTo(userDetails);
|
||||
verify(beans).getBean(beanName, UserDetailsService.class);
|
||||
}
|
||||
@@ -110,8 +112,7 @@ public class WithUserDetailsSecurityContextFactoryTests {
|
||||
when(this.reactiveUserDetailsService.findByUsername(username)).thenReturn(Mono.just(userDetails));
|
||||
|
||||
SecurityContext context = factory.createSecurityContext(withUserDetails);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getPrincipal()).isEqualTo(userDetails);
|
||||
verify(this.beans).getBean(ReactiveUserDetailsService.class);
|
||||
}
|
||||
@@ -122,13 +123,14 @@ public class WithUserDetailsSecurityContextFactoryTests {
|
||||
String username = "user";
|
||||
when(withUserDetails.value()).thenReturn(username);
|
||||
when(withUserDetails.userDetailsServiceBeanName()).thenReturn(beanName);
|
||||
when(this.beans.getBean(beanName, ReactiveUserDetailsService.class)).thenReturn(this.reactiveUserDetailsService);
|
||||
when(this.beans.getBean(beanName, ReactiveUserDetailsService.class))
|
||||
.thenReturn(this.reactiveUserDetailsService);
|
||||
when(this.reactiveUserDetailsService.findByUsername(username)).thenReturn(Mono.just(userDetails));
|
||||
|
||||
SecurityContext context = factory.createSecurityContext(withUserDetails);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getPrincipal()).isEqualTo(userDetails);
|
||||
verify(this.beans).getBean(beanName, ReactiveUserDetailsService.class);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+8
-8
@@ -25,12 +25,10 @@ public class WithUserDetailsTests {
|
||||
|
||||
@Test
|
||||
public void defaults() {
|
||||
WithUserDetails userDetails = AnnotationUtils.findAnnotation(Annotated.class,
|
||||
WithUserDetails.class);
|
||||
WithUserDetails userDetails = AnnotationUtils.findAnnotation(Annotated.class, WithUserDetails.class);
|
||||
assertThat(userDetails.value()).isEqualTo("user");
|
||||
|
||||
WithSecurityContext context = AnnotatedElementUtils
|
||||
.findMergedAnnotation(Annotated.class,
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(Annotated.class,
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
@@ -38,12 +36,12 @@ public class WithUserDetailsTests {
|
||||
|
||||
@WithUserDetails
|
||||
private static class Annotated {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupExplicitThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils
|
||||
.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupExplicit.class,
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_METHOD);
|
||||
@@ -51,12 +49,12 @@ public class WithUserDetailsTests {
|
||||
|
||||
@WithUserDetails(setupBefore = TestExecutionEvent.TEST_METHOD)
|
||||
private class SetupExplicit {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void findMergedAnnotationWhenSetupOverriddenThenOverridden() {
|
||||
WithSecurityContext context = AnnotatedElementUtils
|
||||
.findMergedAnnotation(SetupOverridden.class,
|
||||
WithSecurityContext context = AnnotatedElementUtils.findMergedAnnotation(SetupOverridden.class,
|
||||
WithSecurityContext.class);
|
||||
|
||||
assertThat(context.setupBefore()).isEqualTo(TestExecutionEvent.TEST_EXECUTION);
|
||||
@@ -64,5 +62,7 @@ public class WithUserDetailsTests {
|
||||
|
||||
@WithUserDetails(setupBefore = TestExecutionEvent.TEST_EXECUTION)
|
||||
private class SetupOverridden {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+8
-4
@@ -34,13 +34,12 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
* @since 5.0
|
||||
*/
|
||||
abstract class AbstractMockServerConfigurersTests {
|
||||
|
||||
protected PrincipalController controller = new PrincipalController();
|
||||
|
||||
protected SecurityContextController securityContextController = new SecurityContextController();
|
||||
|
||||
protected User.UserBuilder userBuilder = User
|
||||
.withUsername("user")
|
||||
.password("password")
|
||||
.roles("USER");
|
||||
protected User.UserBuilder userBuilder = User.withUsername("user").password("password").roles("USER");
|
||||
|
||||
protected void assertPrincipalCreatedFromUserDetails(Principal principal, UserDetails originalUserDetails) {
|
||||
assertThat(principal).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
@@ -56,6 +55,7 @@ abstract class AbstractMockServerConfigurersTests {
|
||||
|
||||
@RestController
|
||||
protected static class PrincipalController {
|
||||
|
||||
volatile Principal principal;
|
||||
|
||||
@RequestMapping("/**")
|
||||
@@ -74,10 +74,12 @@ abstract class AbstractMockServerConfigurersTests {
|
||||
assertThat(this.principal).isEqualTo(expected);
|
||||
this.principal = null;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@RestController
|
||||
protected static class SecurityContextController {
|
||||
|
||||
volatile SecurityContext securityContext;
|
||||
|
||||
@RequestMapping("/**")
|
||||
@@ -91,5 +93,7 @@ abstract class AbstractMockServerConfigurersTests {
|
||||
this.securityContext = null;
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+19
-48
@@ -45,31 +45,24 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
*/
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
private GrantedAuthority authority1 = new SimpleGrantedAuthority("one");
|
||||
|
||||
private GrantedAuthority authority2 = new SimpleGrantedAuthority("two");
|
||||
|
||||
private WebTestClient client = WebTestClient
|
||||
.bindToController(securityContextController)
|
||||
private WebTestClient client = WebTestClient.bindToController(securityContextController)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.argumentResolvers(resolvers -> resolvers.addCustomResolver(
|
||||
new CurrentSecurityContextArgumentResolver(new ReactiveAdapterRegistry())))
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
.argumentResolvers(resolvers -> resolvers
|
||||
.addCustomResolver(new CurrentSecurityContextArgumentResolver(new ReactiveAdapterRegistry())))
|
||||
.apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
@Test
|
||||
public void mockOpaqueTokenWhenUsingDefaultsThenBearerTokenAuthentication() {
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken())
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOpaqueToken()).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
BearerTokenAuthentication.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(BearerTokenAuthentication.class);
|
||||
BearerTokenAuthentication token = (BearerTokenAuthentication) context.getAuthentication();
|
||||
assertThat(token.getAuthorities()).isNotEmpty();
|
||||
assertThat(token.getToken()).isNotNull();
|
||||
@@ -78,27 +71,19 @@ public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockSe
|
||||
|
||||
@Test
|
||||
public void mockOpaqueTokenWhenAuthoritiesThenBearerTokenAuthentication() {
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken()
|
||||
.authorities(this.authority1, this.authority2))
|
||||
.get()
|
||||
.exchange()
|
||||
this.client.mutateWith(mockOpaqueToken().authorities(this.authority1, this.authority2)).get().exchange()
|
||||
.expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(this.authority1, this.authority2);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(this.authority1,
|
||||
this.authority2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockOpaqueTokenWhenAttributesThenBearerTokenAuthentication() {
|
||||
String sub = new String("my-subject");
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken()
|
||||
.attributes(attributes -> attributes.put(SUBJECT, sub)))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOpaqueToken().attributes(attributes -> attributes.put(SUBJECT, sub))).get()
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(BearerTokenAuthentication.class);
|
||||
@@ -109,12 +94,7 @@ public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockSe
|
||||
@Test
|
||||
public void mockOpaqueTokenWhenPrincipalThenBearerTokenAuthentication() {
|
||||
OAuth2AuthenticatedPrincipal principal = active();
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken()
|
||||
.principal(principal))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOpaqueToken().principal(principal)).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(BearerTokenAuthentication.class);
|
||||
@@ -126,13 +106,8 @@ public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockSe
|
||||
public void mockOpaqueTokenWhenPrincipalSpecifiedThenLastCalledTakesPrecedence() {
|
||||
OAuth2AuthenticatedPrincipal principal = active(a -> a.put("scope", "user"));
|
||||
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken()
|
||||
.attributes(a -> a.put(SUBJECT, "foo"))
|
||||
.principal(principal))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOpaqueToken().attributes(a -> a.put(SUBJECT, "foo")).principal(principal)).get()
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(BearerTokenAuthentication.class);
|
||||
@@ -140,13 +115,8 @@ public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockSe
|
||||
assertThat((String) ((OAuth2AuthenticatedPrincipal) token.getPrincipal()).getAttribute(SUBJECT))
|
||||
.isEqualTo(principal.getAttribute(SUBJECT));
|
||||
|
||||
this.client
|
||||
.mutateWith(mockOpaqueToken()
|
||||
.principal(principal)
|
||||
.attributes(a -> a.put(SUBJECT, "bar")))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOpaqueToken().principal(principal).attributes(a -> a.put(SUBJECT, "bar"))).get()
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(BearerTokenAuthentication.class);
|
||||
@@ -154,4 +124,5 @@ public class SecurityMockServerConfigurerOpaqueTokenTests extends AbstractMockSe
|
||||
assertThat((String) ((OAuth2AuthenticatedPrincipal) token.getPrincipal()).getAttribute(SUBJECT))
|
||||
.isEqualTo("bar");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+25
-72
@@ -42,21 +42,14 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
@SecurityTestExecutionListeners
|
||||
public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
WebTestClient client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
WebTestClient client = WebTestClient.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void withMockUserWhenOnMethodThenSuccess() {
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.get().exchange().expectStatus().isOk();
|
||||
|
||||
Authentication authentication = TestSecurityContextHolder.getContext().getAuthentication();
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
@@ -65,20 +58,13 @@ public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockSer
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void withMockUserWhenGlobalMockPrincipalThenOverridesAnnotation() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.apply(mockAuthentication(authentication))
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
client = WebTestClient.bindToController(controller).webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity()).apply(mockAuthentication(authentication)).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.get().exchange().expectStatus().isOk();
|
||||
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
}
|
||||
@@ -86,12 +72,9 @@ public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockSer
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void withMockUserWhenMutateWithMockPrincipalThenOverridesAnnotation() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
client
|
||||
.mutateWith(mockAuthentication(authentication))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
client.mutateWith(mockAuthentication(authentication)).get().exchange().expectStatus().isOk();
|
||||
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
}
|
||||
@@ -99,20 +82,13 @@ public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockSer
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void withMockUserWhenMutateWithMockPrincipalAndNoMutateThenOverridesAnnotationAndUsesAnnotation() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
client
|
||||
.mutateWith(mockAuthentication(authentication))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
client.mutateWith(mockAuthentication(authentication)).get().exchange().expectStatus().isOk();
|
||||
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
|
||||
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.get().exchange().expectStatus().isOk();
|
||||
|
||||
assertPrincipalCreatedFromUserDetails(controller.removePrincipal(), userBuilder.build());
|
||||
}
|
||||
@@ -121,16 +97,7 @@ public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockSer
|
||||
@WithMockUser
|
||||
public void withMockUserWhenOnMethodAndRequestIsExecutedOnDifferentThreadThenSuccess() {
|
||||
Authentication authentication = TestSecurityContextHolder.getContext().getAuthentication();
|
||||
ForkJoinPool
|
||||
.commonPool()
|
||||
.submit(() ->
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus()
|
||||
.isOk()
|
||||
)
|
||||
.join();
|
||||
ForkJoinPool.commonPool().submit(() -> client.get().exchange().expectStatus().isOk()).join();
|
||||
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
}
|
||||
@@ -138,32 +105,18 @@ public class SecurityMockServerConfigurersAnnotatedTests extends AbstractMockSer
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void withMockUserAndWithCallOnSeparateThreadWhenMutateWithMockPrincipalAndNoMutateThenOverridesAnnotationAndUsesAnnotation() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
|
||||
ForkJoinPool
|
||||
.commonPool()
|
||||
.submit(() ->
|
||||
client
|
||||
.mutateWith(mockAuthentication(authentication))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
)
|
||||
.join();
|
||||
ForkJoinPool.commonPool().submit(
|
||||
() -> client.mutateWith(mockAuthentication(authentication)).get().exchange().expectStatus().isOk())
|
||||
.join();
|
||||
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
|
||||
|
||||
ForkJoinPool
|
||||
.commonPool()
|
||||
.submit(() ->
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
)
|
||||
.join();
|
||||
ForkJoinPool.commonPool().submit(() -> client.get().exchange().expectStatus().isOk()).join();
|
||||
|
||||
assertPrincipalCreatedFromUserDetails(controller.removePrincipal(), userBuilder.build());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+12
-23
@@ -42,21 +42,15 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
@RunWith(SpringRunner.class)
|
||||
@SecurityTestExecutionListeners
|
||||
public class SecurityMockServerConfigurersClassAnnotatedTests extends AbstractMockServerConfigurersTests {
|
||||
WebTestClient client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
|
||||
WebTestClient client = WebTestClient.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
@Test
|
||||
public void wheMockUserWhenClassAnnotatedThenSuccess() {
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
.expectBody(String.class).consumeWith( response -> assertThat(response.getResponseBody()).contains("\"username\":\"user\""));
|
||||
client.get().exchange().expectStatus().isOk().expectBody(String.class)
|
||||
.consumeWith(response -> assertThat(response.getResponseBody()).contains("\"username\":\"user\""));
|
||||
|
||||
Authentication authentication = TestSecurityContextHolder.getContext().getAuthentication();
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
@@ -65,11 +59,8 @@ public class SecurityMockServerConfigurersClassAnnotatedTests extends AbstractMo
|
||||
@Test
|
||||
@WithMockUser("method-user")
|
||||
public void withMockUserWhenClassAndMethodAnnotationThenMethodOverrides() {
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
.expectBody(String.class).consumeWith( response -> assertThat(response.getResponseBody()).contains("\"username\":\"method-user\""));
|
||||
client.get().exchange().expectStatus().isOk().expectBody(String.class).consumeWith(
|
||||
response -> assertThat(response.getResponseBody()).contains("\"username\":\"method-user\""));
|
||||
|
||||
Authentication authentication = TestSecurityContextHolder.getContext().getAuthentication();
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
@@ -77,14 +68,12 @@ public class SecurityMockServerConfigurersClassAnnotatedTests extends AbstractMo
|
||||
|
||||
@Test
|
||||
public void withMockUserWhenMutateWithThenMustateWithOverrides() {
|
||||
client
|
||||
.mutateWith(mockUser("mutateWith-mockUser"))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
.expectBody(String.class).consumeWith( response -> assertThat(response.getResponseBody()).contains("\"username\":\"mutateWith-mockUser\""));
|
||||
client.mutateWith(mockUser("mutateWith-mockUser")).get().exchange().expectStatus().isOk()
|
||||
.expectBody(String.class).consumeWith(response -> assertThat(response.getResponseBody())
|
||||
.contains("\"username\":\"mutateWith-mockUser\""));
|
||||
|
||||
Principal principal = controller.removePrincipal();
|
||||
assertPrincipalCreatedFromUserDetails(principal, userBuilder.username("mutateWith-mockUser").build());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+24
-56
@@ -47,33 +47,26 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
*/
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockServerConfigurersJwtTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
@Mock
|
||||
GrantedAuthority authority1;
|
||||
|
||||
@Mock
|
||||
GrantedAuthority authority2;
|
||||
|
||||
WebTestClient client = WebTestClient
|
||||
.bindToController(securityContextController)
|
||||
WebTestClient client = WebTestClient.bindToController(securityContextController)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.argumentResolvers(resolvers -> resolvers.addCustomResolver(
|
||||
new CurrentSecurityContextArgumentResolver(new ReactiveAdapterRegistry())))
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
.argumentResolvers(resolvers -> resolvers
|
||||
.addCustomResolver(new CurrentSecurityContextArgumentResolver(new ReactiveAdapterRegistry())))
|
||||
.apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
@Test
|
||||
public void mockJwtWhenUsingDefaultsTheCreatesJwtAuthentication() {
|
||||
client
|
||||
.mutateWith(mockJwt())
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockJwt()).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
JwtAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(JwtAuthenticationToken.class);
|
||||
JwtAuthenticationToken token = (JwtAuthenticationToken) context.getAuthentication();
|
||||
assertThat(token.getAuthorities()).isNotEmpty();
|
||||
assertThat(token.getToken()).isNotNull();
|
||||
@@ -84,79 +77,54 @@ public class SecurityMockServerConfigurersJwtTests extends AbstractMockServerCon
|
||||
@Test
|
||||
public void mockJwtWhenProvidingBuilderConsumerThenProducesJwtAuthentication() {
|
||||
String name = new String("user");
|
||||
client
|
||||
.mutateWith(mockJwt().jwt(jwt -> jwt.subject(name)))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockJwt().jwt(jwt -> jwt.subject(name))).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
JwtAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(JwtAuthenticationToken.class);
|
||||
JwtAuthenticationToken token = (JwtAuthenticationToken) context.getAuthentication();
|
||||
assertThat(token.getToken().getSubject()).isSameAs(name);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockJwtWhenProvidingCustomAuthoritiesThenProducesJwtAuthentication() {
|
||||
client
|
||||
.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "ignored authorities"))
|
||||
.authorities(this.authority1, this.authority2))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "ignored authorities")).authorities(this.authority1,
|
||||
this.authority2)).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(this.authority1, this.authority2);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(this.authority1,
|
||||
this.authority2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockJwtWhenProvidingScopedAuthoritiesThenProducesJwtAuthentication() {
|
||||
client
|
||||
.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "scoped authorities")))
|
||||
.get()
|
||||
.exchange()
|
||||
client.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "scoped authorities"))).get().exchange()
|
||||
.expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(new SimpleGrantedAuthority("SCOPE_scoped"),
|
||||
new SimpleGrantedAuthority("SCOPE_authorities"));
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(
|
||||
new SimpleGrantedAuthority("SCOPE_scoped"), new SimpleGrantedAuthority("SCOPE_authorities"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockJwtWhenProvidingGrantedAuthoritiesThenProducesJwtAuthentication() {
|
||||
client
|
||||
.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "ignored authorities"))
|
||||
.authorities(jwt -> Arrays.asList(this.authority1)))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockJwt().jwt(jwt -> jwt.claim("scope", "ignored authorities"))
|
||||
.authorities(jwt -> Arrays.asList(this.authority1))).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(this.authority1);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(this.authority1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockJwtWhenProvidingPreparedJwtThenProducesJwtAuthentication() {
|
||||
Jwt originalToken = TestJwts.jwt()
|
||||
.header("header1", "value1")
|
||||
.subject("some_user")
|
||||
.build();
|
||||
this.client
|
||||
.mutateWith(mockJwt().jwt(originalToken))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
Jwt originalToken = TestJwts.jwt().header("header1", "value1").subject("some_user").build();
|
||||
this.client.mutateWith(mockJwt().jwt(originalToken)).get().exchange().expectStatus().isOk();
|
||||
|
||||
SecurityContext context = securityContextController.removeSecurityContext();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
JwtAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(JwtAuthenticationToken.class);
|
||||
JwtAuthenticationToken retrievedToken = (JwtAuthenticationToken) context.getAuthentication();
|
||||
assertThat(retrievedToken.getToken().getSubject()).isEqualTo("some_user");
|
||||
assertThat(retrievedToken.getToken().getTokenValue()).isEqualTo("token");
|
||||
assertThat(retrievedToken.getToken().getHeaders().get("header1")).isEqualTo("value1");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+36
-63
@@ -54,6 +54,7 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
private OAuth2LoginController controller = new OAuth2LoginController();
|
||||
|
||||
@Mock
|
||||
@@ -66,36 +67,26 @@ public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMock
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
this.client = WebTestClient
|
||||
.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(
|
||||
new OAuth2AuthorizedClientArgumentResolver
|
||||
(this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
this.client = WebTestClient.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(new OAuth2AuthorizedClientArgumentResolver(
|
||||
this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsingDefaultsThenException()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenUsingDefaultsThenException() throws Exception {
|
||||
|
||||
WebHttpHandlerBuilder builder = WebHttpHandlerBuilder.webHandler(new DispatcherHandler());
|
||||
assertThatCode(() -> mockOAuth2Client().beforeServerCreated(builder))
|
||||
.isInstanceOf(IllegalArgumentException.class)
|
||||
.hasMessageContaining("ClientRegistration");
|
||||
.isInstanceOf(IllegalArgumentException.class).hasMessageContaining("ClientRegistration");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsingRegistrationIdThenProducesAuthorizedClient()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenUsingRegistrationIdThenProducesAuthorizedClient() throws Exception {
|
||||
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id"))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id")).get().uri("/client").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -105,15 +96,12 @@ public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMock
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenClientRegistrationThenUses()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenClientRegistrationThenUses() throws Exception {
|
||||
|
||||
ClientRegistration clientRegistration = clientRegistration()
|
||||
.registrationId("registration-id").clientId("client-id").build();
|
||||
this.client.mutateWith(mockOAuth2Client().clientRegistration(clientRegistration))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
ClientRegistration clientRegistration = clientRegistration().registrationId("registration-id")
|
||||
.clientId("client-id").build();
|
||||
this.client.mutateWith(mockOAuth2Client().clientRegistration(clientRegistration)).get().uri("/client")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -123,14 +111,10 @@ public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMock
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenClientRegistrationConsumerThenUses()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenClientRegistrationConsumerThenUses() throws Exception {
|
||||
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id")
|
||||
.clientRegistration(c -> c.clientId("client-id")))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id").clientRegistration(c -> c.clientId("client-id")))
|
||||
.get().uri("/client").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -142,24 +126,16 @@ public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMock
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenPrincipalNameThenUses() throws Exception {
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id")
|
||||
.principalName("test-subject"))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk()
|
||||
.expectBody(String.class).isEqualTo("test-subject");
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id").principalName("test-subject")).get().uri("/client")
|
||||
.exchange().expectStatus().isOk().expectBody(String.class).isEqualTo("test-subject");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenAccessTokenThenUses()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenAccessTokenThenUses() throws Exception {
|
||||
|
||||
OAuth2AccessToken accessToken = noScopes();
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id")
|
||||
.accessToken(accessToken))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id").accessToken(accessToken)).get().uri("/client")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -170,39 +146,36 @@ public class SecurityMockServerConfigurersOAuth2ClientTests extends AbstractMock
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsedOnceThenDoesNotAffectRemainingTests() throws Exception {
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id"))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Client("registration-id")).get().uri("/client").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
assertThat(client.getClientRegistration().getClientId()).isEqualTo("test-client");
|
||||
|
||||
client = new OAuth2AuthorizedClient(clientRegistration().build(), "sub", noScopes());
|
||||
when(this.authorizedClientRepository
|
||||
.loadAuthorizedClient(eq("registration-id"), any(Authentication.class), any(ServerWebExchange.class)))
|
||||
.thenReturn(Mono.just(client));
|
||||
this.client
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
when(this.authorizedClientRepository.loadAuthorizedClient(eq("registration-id"), any(Authentication.class),
|
||||
any(ServerWebExchange.class))).thenReturn(Mono.just(client));
|
||||
this.client.get().uri("/client").exchange().expectStatus().isOk();
|
||||
client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
assertThat(client.getClientRegistration().getClientId()).isEqualTo("client-id");
|
||||
verify(this.authorizedClientRepository).loadAuthorizedClient(
|
||||
eq("registration-id"), any(Authentication.class), any(ServerWebExchange.class));
|
||||
verify(this.authorizedClientRepository).loadAuthorizedClient(eq("registration-id"), any(Authentication.class),
|
||||
any(ServerWebExchange.class));
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class OAuth2LoginController {
|
||||
|
||||
volatile OAuth2AuthorizedClient authorizedClient;
|
||||
|
||||
@GetMapping("/client")
|
||||
String authorizedClient
|
||||
(@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
String authorizedClient(
|
||||
@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
this.authorizedClient = authorizedClient;
|
||||
return authorizedClient.getPrincipalName();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+35
-72
@@ -49,6 +49,7 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockServerConfigurersOAuth2LoginTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
private OAuth2LoginController controller = new OAuth2LoginController();
|
||||
|
||||
@Mock
|
||||
@@ -61,41 +62,29 @@ public class SecurityMockServerConfigurersOAuth2LoginTests extends AbstractMockS
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
this.client = WebTestClient
|
||||
.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(
|
||||
new OAuth2AuthorizedClientArgumentResolver
|
||||
(this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
this.client = WebTestClient.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(new OAuth2AuthorizedClientArgumentResolver(
|
||||
this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthentication() {
|
||||
this.client.mutateWith(mockOAuth2Login())
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login()).get().uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token).isNotNull();
|
||||
assertThat(token.getAuthorizedClientRegistrationId()).isEqualTo("test");
|
||||
assertThat(token.getPrincipal()).isInstanceOf(OAuth2User.class);
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "user");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "user");
|
||||
assertThat((Collection<GrantedAuthority>) token.getPrincipal().getAuthorities())
|
||||
.contains(new SimpleGrantedAuthority("SCOPE_read"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient() {
|
||||
this.client.mutateWith(mockOAuth2Login())
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login()).get().uri("/client").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -106,11 +95,8 @@ public class SecurityMockServerConfigurersOAuth2LoginTests extends AbstractMockS
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenAuthoritiesSpecifiedThenGrantsAccess() {
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.authorities(new SimpleGrantedAuthority("SCOPE_admin")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().authorities(new SimpleGrantedAuthority("SCOPE_admin"))).get()
|
||||
.uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat((Collection<GrantedAuthority>) token.getPrincipal().getAuthorities())
|
||||
@@ -119,78 +105,54 @@ public class SecurityMockServerConfigurersOAuth2LoginTests extends AbstractMockS
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenAttributeSpecifiedThenUserHasAttribute() {
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.attributes(a -> a.put("iss", "https://idp.example.org")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().attributes(a -> a.put("iss", "https://idp.example.org"))).get()
|
||||
.uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("iss", "https://idp.example.org");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("iss", "https://idp.example.org");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenNameSpecifiedThenUserHasName() throws Exception {
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(
|
||||
AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("custom-attribute", "test-subject"),
|
||||
"custom-attribute");
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("custom-attribute", "test-subject"), "custom-attribute");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.oauth2User(oauth2User))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().oauth2User(oauth2User)).get().uri("/token").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getName())
|
||||
.isEqualTo("test-subject");
|
||||
assertThat(token.getPrincipal().getName()).isEqualTo("test-subject");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.oauth2User(oauth2User))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().oauth2User(oauth2User)).get().uri("/client").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client.getPrincipalName())
|
||||
.isEqualTo("test-subject");
|
||||
assertThat(client.getPrincipalName()).isEqualTo("test-subject");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenOAuth2UserSpecifiedThenLastCalledTakesPrecedence() throws Exception {
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(
|
||||
AuthorityUtils.createAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("sub", "subject"),
|
||||
"sub");
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(AuthorityUtils.createAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("sub", "subject"), "sub");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.attributes(a -> a.put("subject", "foo"))
|
||||
.oauth2User(oauth2User))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().attributes(a -> a.put("subject", "foo")).oauth2User(oauth2User)).get()
|
||||
.uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "subject");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "subject");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.oauth2User(oauth2User)
|
||||
.attributes(a -> a.put("sub", "bar")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().oauth2User(oauth2User).attributes(a -> a.put("sub", "bar"))).get()
|
||||
.uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "bar");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "bar");
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class OAuth2LoginController {
|
||||
|
||||
volatile OAuth2AuthenticationToken token;
|
||||
|
||||
volatile OAuth2AuthorizedClient authorizedClient;
|
||||
|
||||
@GetMapping("/token")
|
||||
@@ -200,10 +162,11 @@ public class SecurityMockServerConfigurersOAuth2LoginTests extends AbstractMockS
|
||||
}
|
||||
|
||||
@GetMapping("/client")
|
||||
String authorizedClient
|
||||
(@RegisteredOAuth2AuthorizedClient OAuth2AuthorizedClient authorizedClient) {
|
||||
String authorizedClient(@RegisteredOAuth2AuthorizedClient OAuth2AuthorizedClient authorizedClient) {
|
||||
this.authorizedClient = authorizedClient;
|
||||
return authorizedClient.getPrincipalName();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+37
-77
@@ -51,6 +51,7 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockServerConfigurersOidcLoginTests extends AbstractMockServerConfigurersTests {
|
||||
|
||||
private OAuth2LoginController controller = new OAuth2LoginController();
|
||||
|
||||
@Mock
|
||||
@@ -63,43 +64,30 @@ public class SecurityMockServerConfigurersOidcLoginTests extends AbstractMockSer
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
this.client = WebTestClient
|
||||
.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(
|
||||
new OAuth2AuthorizedClientArgumentResolver
|
||||
(this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
this.client = WebTestClient.bindToController(this.controller)
|
||||
.argumentResolvers(c -> c.addCustomResolver(new OAuth2AuthorizedClientArgumentResolver(
|
||||
this.clientRegistrationRepository, this.authorizedClientRepository)))
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthentication() {
|
||||
this.client.mutateWith(mockOidcLogin())
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin()).get().uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token).isNotNull();
|
||||
assertThat(token.getAuthorizedClientRegistrationId()).isEqualTo("test");
|
||||
assertThat(token.getPrincipal()).isInstanceOf(OidcUser.class);
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "user");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "user");
|
||||
assertThat((Collection<GrantedAuthority>) token.getPrincipal().getAuthorities())
|
||||
.contains(new SimpleGrantedAuthority("SCOPE_read"));
|
||||
assertThat(((OidcUser) token.getPrincipal()).getIdToken().getTokenValue())
|
||||
.isEqualTo("id-token");
|
||||
assertThat(((OidcUser) token.getPrincipal()).getIdToken().getTokenValue()).isEqualTo("id-token");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient() {
|
||||
this.client.mutateWith(mockOidcLogin())
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin()).get().uri("/client").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client).isNotNull();
|
||||
@@ -110,11 +98,8 @@ public class SecurityMockServerConfigurersOidcLoginTests extends AbstractMockSer
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenAuthoritiesSpecifiedThenGrantsAccess() {
|
||||
this.client.mutateWith(mockOidcLogin()
|
||||
.authorities(new SimpleGrantedAuthority("SCOPE_admin")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin().authorities(new SimpleGrantedAuthority("SCOPE_admin"))).get()
|
||||
.uri("/token").exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat((Collection<GrantedAuthority>) token.getPrincipal().getAuthorities())
|
||||
@@ -123,90 +108,64 @@ public class SecurityMockServerConfigurersOidcLoginTests extends AbstractMockSer
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenIdTokenSpecifiedThenUserHasClaims() {
|
||||
this.client.mutateWith(mockOidcLogin()
|
||||
.idToken(i -> i.issuer("https://idp.example.org")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin().idToken(i -> i.issuer("https://idp.example.org"))).get().uri("/token")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("iss", "https://idp.example.org");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("iss", "https://idp.example.org");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUserInfoSpecifiedThenUserHasClaims() throws Exception {
|
||||
this.client.mutateWith(mockOidcLogin()
|
||||
.userInfoToken(u -> u.email("email@email")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin().userInfoToken(u -> u.email("email@email"))).get().uri("/token")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("email", "email@email");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("email", "email@email");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcUserWhenNameSpecifiedThenUserHasName() throws Exception {
|
||||
OidcUser oidcUser = new DefaultOidcUser(
|
||||
AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
OidcUser oidcUser = new DefaultOidcUser(AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
OidcIdToken.withTokenValue("id-token").claim("custom-attribute", "test-subject").build(),
|
||||
"custom-attribute");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.oauth2User(oidcUser))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().oauth2User(oidcUser)).get().uri("/token").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getName())
|
||||
.isEqualTo("test-subject");
|
||||
assertThat(token.getPrincipal().getName()).isEqualTo("test-subject");
|
||||
|
||||
this.client.mutateWith(mockOAuth2Login()
|
||||
.oauth2User(oidcUser))
|
||||
.get().uri("/client")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOAuth2Login().oauth2User(oidcUser)).get().uri("/client").exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
OAuth2AuthorizedClient client = this.controller.authorizedClient;
|
||||
assertThat(client.getPrincipalName())
|
||||
.isEqualTo("test-subject");
|
||||
assertThat(client.getPrincipalName()).isEqualTo("test-subject");
|
||||
}
|
||||
|
||||
// gh-7794
|
||||
@Test
|
||||
public void oidcLoginWhenOidcUserSpecifiedThenLastCalledTakesPrecedence() throws Exception {
|
||||
OidcUser oidcUser = new DefaultOidcUser(
|
||||
AuthorityUtils.createAuthorityList("SCOPE_read"), idToken().build());
|
||||
OidcUser oidcUser = new DefaultOidcUser(AuthorityUtils.createAuthorityList("SCOPE_read"), idToken().build());
|
||||
|
||||
this.client.mutateWith(mockOidcLogin()
|
||||
.idToken(i -> i.subject("foo"))
|
||||
.oidcUser(oidcUser))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin().idToken(i -> i.subject("foo")).oidcUser(oidcUser)).get().uri("/token")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
OAuth2AuthenticationToken token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "subject");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "subject");
|
||||
|
||||
this.client.mutateWith(mockOidcLogin()
|
||||
.oidcUser(oidcUser)
|
||||
.idToken(i -> i.subject("bar")))
|
||||
.get().uri("/token")
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(mockOidcLogin().oidcUser(oidcUser).idToken(i -> i.subject("bar"))).get().uri("/token")
|
||||
.exchange().expectStatus().isOk();
|
||||
|
||||
token = this.controller.token;
|
||||
assertThat(token.getPrincipal().getAttributes())
|
||||
.containsEntry("sub", "bar");
|
||||
assertThat(token.getPrincipal().getAttributes()).containsEntry("sub", "bar");
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class OAuth2LoginController {
|
||||
|
||||
volatile OAuth2AuthenticationToken token;
|
||||
|
||||
volatile OAuth2AuthorizedClient authorizedClient;
|
||||
|
||||
@GetMapping("/token")
|
||||
@@ -216,10 +175,11 @@ public class SecurityMockServerConfigurersOidcLoginTests extends AbstractMockSer
|
||||
}
|
||||
|
||||
@GetMapping("/client")
|
||||
String authorizedClient
|
||||
(@RegisteredOAuth2AuthorizedClient OAuth2AuthorizedClient authorizedClient) {
|
||||
String authorizedClient(@RegisteredOAuth2AuthorizedClient OAuth2AuthorizedClient authorizedClient) {
|
||||
this.authorizedClient = authorizedClient;
|
||||
return authorizedClient.getPrincipalName();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+29
-79
@@ -37,50 +37,33 @@ import static org.springframework.security.test.web.reactive.server.SecurityMock
|
||||
* @since 5.0
|
||||
*/
|
||||
public class SecurityMockServerConfigurersTests extends AbstractMockServerConfigurersTests {
|
||||
WebTestClient client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter( new CsrfWebFilter(), new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
|
||||
WebTestClient client = WebTestClient.bindToController(controller)
|
||||
.webFilter(new CsrfWebFilter(), new SecurityContextServerWebExchangeWebFilter()).apply(springSecurity())
|
||||
.configureClient().defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
|
||||
@Test
|
||||
public void mockAuthenticationWhenLocalThenSuccess() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
client
|
||||
.mutateWith(mockAuthentication(authentication))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
client.mutateWith(mockAuthentication(authentication)).get().exchange().expectStatus().isOk();
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockAuthenticationWhenGlobalThenSuccess() {
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret", "ROLE_USER");
|
||||
client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.apply(mockAuthentication(authentication))
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
TestingAuthenticationToken authentication = new TestingAuthenticationToken("authentication", "secret",
|
||||
"ROLE_USER");
|
||||
client = WebTestClient.bindToController(controller).webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity()).apply(mockAuthentication(authentication)).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
client.get().exchange().expectStatus().isOk();
|
||||
controller.assertPrincipalIsEqualTo(authentication);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void mockUserWhenDefaultsThenSuccess() {
|
||||
client
|
||||
.mutateWith(mockUser())
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockUser()).get().exchange().expectStatus().isOk();
|
||||
|
||||
Principal actual = controller.removePrincipal();
|
||||
|
||||
@@ -89,18 +72,10 @@ public class SecurityMockServerConfigurersTests extends AbstractMockServerConfig
|
||||
|
||||
@Test
|
||||
public void mockUserWhenGlobalThenSuccess() {
|
||||
client = WebTestClient
|
||||
.bindToController(controller)
|
||||
.webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity())
|
||||
.apply(mockUser())
|
||||
.configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.build();
|
||||
client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client = WebTestClient.bindToController(controller).webFilter(new SecurityContextServerWebExchangeWebFilter())
|
||||
.apply(springSecurity()).apply(mockUser()).configureClient()
|
||||
.defaultHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).build();
|
||||
client.get().exchange().expectStatus().isOk();
|
||||
|
||||
Principal actual = controller.removePrincipal();
|
||||
|
||||
@@ -109,11 +84,7 @@ public class SecurityMockServerConfigurersTests extends AbstractMockServerConfig
|
||||
|
||||
@Test
|
||||
public void mockUserStringWhenLocalThenSuccess() {
|
||||
client
|
||||
.mutateWith(mockUser(userBuilder.build().getUsername()))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockUser(userBuilder.build().getUsername())).get().exchange().expectStatus().isOk();
|
||||
|
||||
Principal actual = controller.removePrincipal();
|
||||
|
||||
@@ -123,11 +94,8 @@ public class SecurityMockServerConfigurersTests extends AbstractMockServerConfig
|
||||
@Test
|
||||
public void mockUserStringWhenCustomThenSuccess() {
|
||||
this.userBuilder = User.withUsername("admin").password("secret").roles("USER", "ADMIN");
|
||||
client
|
||||
.mutateWith(mockUser("admin").password("secret").roles("USER", "ADMIN"))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockUser("admin").password("secret").roles("USER", "ADMIN")).get().exchange().expectStatus()
|
||||
.isOk();
|
||||
|
||||
Principal actual = controller.removePrincipal();
|
||||
|
||||
@@ -137,11 +105,7 @@ public class SecurityMockServerConfigurersTests extends AbstractMockServerConfig
|
||||
@Test
|
||||
public void mockUserUserDetailsLocalThenSuccess() {
|
||||
UserDetails userDetails = this.userBuilder.build();
|
||||
client
|
||||
.mutateWith(mockUser(userDetails))
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
client.mutateWith(mockUser(userDetails)).get().exchange().expectStatus().isOk();
|
||||
|
||||
Principal actual = controller.removePrincipal();
|
||||
|
||||
@@ -150,34 +114,20 @@ public class SecurityMockServerConfigurersTests extends AbstractMockServerConfig
|
||||
|
||||
@Test
|
||||
public void csrfWhenMutateWithThenDisablesCsrf() {
|
||||
this.client
|
||||
.post()
|
||||
.exchange()
|
||||
.expectStatus().isEqualTo(HttpStatus.FORBIDDEN)
|
||||
.expectBody().consumeWith( b -> assertThat(new String(b.getResponseBody())).contains("CSRF"));
|
||||
this.client.post().exchange().expectStatus().isEqualTo(HttpStatus.FORBIDDEN).expectBody()
|
||||
.consumeWith(b -> assertThat(new String(b.getResponseBody())).contains("CSRF"));
|
||||
|
||||
this.client
|
||||
.mutateWith(csrf())
|
||||
.post()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.mutateWith(csrf()).post().exchange().expectStatus().isOk();
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void csrfWhenGlobalThenDisablesCsrf() {
|
||||
this.client = WebTestClient
|
||||
.bindToController(this.controller)
|
||||
.webFilter(new CsrfWebFilter())
|
||||
.apply(springSecurity())
|
||||
.apply(csrf())
|
||||
.configureClient()
|
||||
.build();
|
||||
this.client = WebTestClient.bindToController(this.controller).webFilter(new CsrfWebFilter())
|
||||
.apply(springSecurity()).apply(csrf()).configureClient().build();
|
||||
|
||||
this.client
|
||||
.get()
|
||||
.exchange()
|
||||
.expectStatus().isOk();
|
||||
this.client.get().exchange().expectStatus().isOk();
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+26
-52
@@ -44,7 +44,6 @@ import org.springframework.web.context.WebApplicationContext;
|
||||
* @author Rob Winch
|
||||
*/
|
||||
|
||||
|
||||
@RunWith(SpringJUnit4ClassRunner.class)
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
@@ -57,89 +56,62 @@ public class Sec2935Tests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.apply(springSecurity())
|
||||
.build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity()).build();
|
||||
}
|
||||
|
||||
// SEC-2935
|
||||
@Test
|
||||
public void postProcessorUserNoUser() throws Exception {
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user").roles("ADMIN", "USER")))
|
||||
.andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
mvc.perform(get("/admin/abc").with(user("user").roles("ADMIN", "USER"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc"))
|
||||
.andExpect(status().isUnauthorized())
|
||||
.andExpect(unauthenticated());
|
||||
mvc.perform(get("/admin/abc")).andExpect(status().isUnauthorized()).andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void postProcessorUserOtherUser() throws Exception {
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER")))
|
||||
.andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
mvc.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user2").roles("USER")))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("user2"));
|
||||
mvc.perform(get("/admin/abc").with(user("user2").roles("USER"))).andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("user2"));
|
||||
}
|
||||
|
||||
@WithMockUser
|
||||
@Test
|
||||
public void postProcessorUserWithMockUser() throws Exception {
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER")))
|
||||
.andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
mvc.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc"))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
mvc.perform(get("/admin/abc")).andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
// SEC-2941
|
||||
@Test
|
||||
public void defaultRequest() throws Exception {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.apply(springSecurity())
|
||||
.defaultRequest(get("/").with(user("default")))
|
||||
.build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity())
|
||||
.defaultRequest(get("/").with(user("default"))).build();
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER")))
|
||||
.andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
mvc.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc"))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("default"));
|
||||
mvc.perform(get("/admin/abc")).andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("default"));
|
||||
}
|
||||
|
||||
@Ignore
|
||||
@WithMockUser
|
||||
@Test
|
||||
public void defaultRequestOverridesWithMockUser() throws Exception {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.apply(springSecurity())
|
||||
.defaultRequest(get("/").with(user("default")))
|
||||
.build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity())
|
||||
.defaultRequest(get("/").with(user("default"))).build();
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER")))
|
||||
.andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
mvc.perform(get("/admin/abc").with(user("user1").roles("ADMIN", "USER"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user1"));
|
||||
|
||||
mvc
|
||||
.perform(get("/admin/abc"))
|
||||
.andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("default"));
|
||||
mvc.perform(get("/admin/abc")).andExpect(status().isForbidden())
|
||||
.andExpect(authenticated().withUsername("default"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -162,5 +134,7 @@ public class Sec2935Tests {
|
||||
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.inMemoryAuthentication();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+13
-17
@@ -39,6 +39,7 @@ import static org.powermock.api.mockito.PowerMockito.when;
|
||||
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
|
||||
|
||||
public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
|
||||
private MockServletContext servletContext;
|
||||
|
||||
@Before
|
||||
@@ -55,16 +56,15 @@ public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
assertThat(request.getParameter("username")).isEqualTo("user");
|
||||
assertThat(request.getParameter("password")).isEqualTo("password");
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName()))
|
||||
.isEqualTo(token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/login");
|
||||
assertThat(request.getParameter("_csrf")).isNotNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void custom() {
|
||||
MockHttpServletRequest request = formLogin("/login").user("username", "admin")
|
||||
.password("password", "secret").buildRequest(this.servletContext);
|
||||
MockHttpServletRequest request = formLogin("/login").user("username", "admin").password("password", "secret")
|
||||
.buildRequest(this.servletContext);
|
||||
|
||||
CsrfToken token = (CsrfToken) request
|
||||
.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
@@ -72,8 +72,7 @@ public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
assertThat(request.getParameter("username")).isEqualTo("admin");
|
||||
assertThat(request.getParameter("password")).isEqualTo("secret");
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName()))
|
||||
.isEqualTo(token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/login");
|
||||
}
|
||||
|
||||
@@ -88,14 +87,13 @@ public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
assertThat(request.getParameter("username")).isEqualTo("admin");
|
||||
assertThat(request.getParameter("password")).isEqualTo("secret");
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName()))
|
||||
.isEqualTo(token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/uri-login/val1/val2");
|
||||
}
|
||||
|
||||
/**
|
||||
* spring-restdocs uses postprocessors to do its trick. It will work only if these are merged together
|
||||
* with our request builders. (gh-7572)
|
||||
* spring-restdocs uses postprocessors to do its trick. It will work only if these are
|
||||
* merged together with our request builders. (gh-7572)
|
||||
* @throws Exception
|
||||
*/
|
||||
@Test
|
||||
@@ -103,9 +101,7 @@ public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
RequestPostProcessor postProcessor = mock(RequestPostProcessor.class);
|
||||
when(postProcessor.postProcessRequest(any())).thenAnswer(i -> i.getArgument(0));
|
||||
MockMvc mockMvc = MockMvcBuilders.standaloneSetup(new Object())
|
||||
.defaultRequest(MockMvcRequestBuilders.get("/").with(postProcessor))
|
||||
.build();
|
||||
|
||||
.defaultRequest(MockMvcRequestBuilders.get("/").with(postProcessor)).build();
|
||||
|
||||
MvcResult mvcResult = mockMvc.perform(formLogin()).andReturn();
|
||||
assertThat(mvcResult.getRequest().getMethod()).isEqualTo(HttpMethod.POST.name());
|
||||
@@ -121,10 +117,10 @@ public class SecurityMockMvcRequestBuildersFormLoginTests {
|
||||
// gh-3920
|
||||
@Test
|
||||
public void usesAcceptMediaForContentNegotiation() {
|
||||
MockHttpServletRequest request = formLogin("/login").user("username", "admin")
|
||||
.password("password", "secret").buildRequest(this.servletContext);
|
||||
MockHttpServletRequest request = formLogin("/login").user("username", "admin").password("password", "secret")
|
||||
.buildRequest(this.servletContext);
|
||||
|
||||
assertThat(request.getHeader("Accept"))
|
||||
.isEqualTo(MediaType.APPLICATION_FORM_URLENCODED_VALUE);
|
||||
assertThat(request.getHeader("Accept")).isEqualTo(MediaType.APPLICATION_FORM_URLENCODED_VALUE);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+17
-17
@@ -39,6 +39,7 @@ import static org.powermock.api.mockito.PowerMockito.when;
|
||||
import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.logout;
|
||||
|
||||
public class SecurityMockMvcRequestBuildersFormLogoutTests {
|
||||
|
||||
private MockServletContext servletContext;
|
||||
|
||||
@Before
|
||||
@@ -50,43 +51,42 @@ public class SecurityMockMvcRequestBuildersFormLogoutTests {
|
||||
public void defaults() {
|
||||
MockHttpServletRequest request = logout().buildRequest(servletContext);
|
||||
|
||||
CsrfToken token = (CsrfToken) request.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
CsrfToken token = (CsrfToken) request
|
||||
.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(
|
||||
token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/logout");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void custom() {
|
||||
MockHttpServletRequest request = logout("/admin/logout").buildRequest(
|
||||
servletContext);
|
||||
MockHttpServletRequest request = logout("/admin/logout").buildRequest(servletContext);
|
||||
|
||||
CsrfToken token = (CsrfToken) request.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
CsrfToken token = (CsrfToken) request
|
||||
.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(
|
||||
token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/admin/logout");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void customWithUriVars() {
|
||||
MockHttpServletRequest request = logout().logoutUrl("/uri-logout/{var1}/{var2}", "val1", "val2").buildRequest(
|
||||
servletContext);
|
||||
MockHttpServletRequest request = logout().logoutUrl("/uri-logout/{var1}/{var2}", "val1", "val2")
|
||||
.buildRequest(servletContext);
|
||||
|
||||
CsrfToken token = (CsrfToken) request.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
CsrfToken token = (CsrfToken) request
|
||||
.getAttribute(CsrfRequestPostProcessor.TestCsrfTokenRepository.TOKEN_ATTR_NAME);
|
||||
|
||||
assertThat(request.getMethod()).isEqualTo("POST");
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(
|
||||
token.getToken());
|
||||
assertThat(request.getParameter(token.getParameterName())).isEqualTo(token.getToken());
|
||||
assertThat(request.getRequestURI()).isEqualTo("/uri-logout/val1/val2");
|
||||
}
|
||||
|
||||
/**
|
||||
* spring-restdocs uses postprocessors to do its trick. It will work only if these are merged together
|
||||
* with our request builders. (gh-7572)
|
||||
* spring-restdocs uses postprocessors to do its trick. It will work only if these are
|
||||
* merged together with our request builders. (gh-7572)
|
||||
* @throws Exception
|
||||
*/
|
||||
@Test
|
||||
@@ -94,8 +94,7 @@ public class SecurityMockMvcRequestBuildersFormLogoutTests {
|
||||
RequestPostProcessor postProcessor = mock(RequestPostProcessor.class);
|
||||
when(postProcessor.postProcessRequest(any())).thenAnswer(i -> i.getArgument(0));
|
||||
MockMvc mockMvc = MockMvcBuilders.standaloneSetup(new Object())
|
||||
.defaultRequest(MockMvcRequestBuilders.get("/").with(postProcessor))
|
||||
.build();
|
||||
.defaultRequest(MockMvcRequestBuilders.get("/").with(postProcessor)).build();
|
||||
|
||||
MvcResult mvcResult = mockMvc.perform(logout()).andReturn();
|
||||
assertThat(mvcResult.getRequest().getMethod()).isEqualTo(HttpMethod.POST.name());
|
||||
@@ -105,4 +104,5 @@ public class SecurityMockMvcRequestBuildersFormLogoutTests {
|
||||
assertThat(mvcResult.getRequest().getParameter("_csrf")).isNotEmpty();
|
||||
verify(postProcessor).postProcessRequest(any());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
@@ -92,10 +92,14 @@ public class SecurityMockMvcRequestPostProcessorsAuthenticationStatelessTests {
|
||||
|
||||
@RestController
|
||||
static class Controller {
|
||||
|
||||
@RequestMapping
|
||||
public String hello() {
|
||||
return "Hello";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+6
-3
@@ -44,10 +44,13 @@ import org.springframework.security.web.context.SecurityContextRepository;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareOnlyThisForTest(WebTestUtils.class)
|
||||
@PowerMockIgnore({"javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*"})
|
||||
@PowerMockIgnore({ "javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*",
|
||||
"javax.xml.parsers.*" })
|
||||
public class SecurityMockMvcRequestPostProcessorsAuthenticationTests {
|
||||
|
||||
@Captor
|
||||
private ArgumentCaptor<SecurityContext> contextCaptor;
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository repository;
|
||||
|
||||
@@ -71,8 +74,7 @@ public class SecurityMockMvcRequestPostProcessorsAuthenticationTests {
|
||||
public void userDetails() {
|
||||
authentication(authentication).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isSameAs(authentication);
|
||||
}
|
||||
@@ -81,4 +83,5 @@ public class SecurityMockMvcRequestPostProcessorsAuthenticationTests {
|
||||
spy(WebTestUtils.class);
|
||||
when(WebTestUtils.getSecurityContextRepository(request)).thenReturn(repository);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+6
-6
@@ -29,6 +29,7 @@ import static org.springframework.security.test.web.servlet.request.SecurityMock
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockMvcRequestPostProcessorsCertificateTests {
|
||||
|
||||
@Mock
|
||||
private X509Certificate certificate;
|
||||
|
||||
@@ -41,8 +42,7 @@ public class SecurityMockMvcRequestPostProcessorsCertificateTests {
|
||||
|
||||
@Test
|
||||
public void x509SingleCertificate() {
|
||||
MockHttpServletRequest postProcessedRequest = x509(certificate)
|
||||
.postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = x509(certificate).postProcessRequest(request);
|
||||
|
||||
X509Certificate[] certificates = (X509Certificate[]) postProcessedRequest
|
||||
.getAttribute("javax.servlet.request.X509Certificate");
|
||||
@@ -52,14 +52,14 @@ public class SecurityMockMvcRequestPostProcessorsCertificateTests {
|
||||
|
||||
@Test
|
||||
public void x509ResourceName() throws Exception {
|
||||
MockHttpServletRequest postProcessedRequest = x509("rod.cer").postProcessRequest(
|
||||
request);
|
||||
MockHttpServletRequest postProcessedRequest = x509("rod.cer").postProcessRequest(request);
|
||||
|
||||
X509Certificate[] certificates = (X509Certificate[]) postProcessedRequest
|
||||
.getAttribute("javax.servlet.request.X509Certificate");
|
||||
|
||||
assertThat(certificates).hasSize(1);
|
||||
assertThat(certificates[0].getSubjectDN().getName()).isEqualTo(
|
||||
"CN=rod, OU=Spring Security, O=Spring Framework");
|
||||
assertThat(certificates[0].getSubjectDN().getName())
|
||||
.isEqualTo("CN=rod, OU=Spring Security, O=Spring Framework");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+3
@@ -53,6 +53,7 @@ public class SecurityMockMvcRequestPostProcessorsCsrfDebugFilterTests {
|
||||
|
||||
@EnableWebSecurity
|
||||
static class Config extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CsrfTokenRepository cookieCsrfTokenRepository = new CookieCsrfTokenRepository();
|
||||
|
||||
@Override
|
||||
@@ -65,5 +66,7 @@ public class SecurityMockMvcRequestPostProcessorsCsrfDebugFilterTests {
|
||||
// Enable the DebugFilter
|
||||
web.debug(true);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+15
-3
@@ -62,10 +62,13 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcRequestPostProcessorsCsrfTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext wac;
|
||||
|
||||
@Autowired
|
||||
TheController controller;
|
||||
|
||||
@Autowired
|
||||
FilterChainProxy springSecurityFilterChain;
|
||||
|
||||
@@ -177,6 +180,7 @@ public class SecurityMockMvcRequestPostProcessorsCsrfTests {
|
||||
assertThat(request.getParameter("_csrf")).isNotNull();
|
||||
assertThat(request.getHeader("X-CSRF-TOKEN")).isNull();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static ResultMatcher csrfAsHeader() {
|
||||
@@ -191,18 +195,19 @@ public class SecurityMockMvcRequestPostProcessorsCsrfTests {
|
||||
assertThat(request.getParameter("_csrf")).isNull();
|
||||
assertThat(request.getHeader("X-CSRF-TOKEN")).isNotNull();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class SessionRepositoryFilter 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(new SessionRequestWrapper(request), response);
|
||||
}
|
||||
|
||||
static class SessionRequestWrapper extends HttpServletRequestWrapper {
|
||||
|
||||
HttpSession session = new MockHttpSession();
|
||||
|
||||
SessionRequestWrapper(HttpServletRequest request) {
|
||||
@@ -218,21 +223,28 @@ public class SecurityMockMvcRequestPostProcessorsCsrfTests {
|
||||
public HttpSession getSession() {
|
||||
return this.session;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class Config extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) {
|
||||
}
|
||||
|
||||
@RestController
|
||||
static class TheController {
|
||||
|
||||
@RequestMapping("/")
|
||||
String index() {
|
||||
return "Hi";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+11
-14
@@ -39,6 +39,7 @@ import static org.springframework.security.test.web.servlet.request.SecurityMock
|
||||
public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
|
||||
private DigestAuthenticationFilter filter;
|
||||
|
||||
private MockHttpServletRequest request;
|
||||
|
||||
private String username;
|
||||
@@ -56,8 +57,8 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
entryPoint.setKey("key");
|
||||
entryPoint.setRealmName("Spring Security");
|
||||
filter = new DigestAuthenticationFilter();
|
||||
filter.setUserDetailsService(username -> new User(username, password, AuthorityUtils
|
||||
.createAuthorityList("ROLE_USER")));
|
||||
filter.setUserDetailsService(
|
||||
username -> new User(username, password, AuthorityUtils.createAuthorityList("ROLE_USER")));
|
||||
filter.setAuthenticationEntryPoint(entryPoint);
|
||||
filter.afterPropertiesSet();
|
||||
}
|
||||
@@ -69,8 +70,7 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
|
||||
@Test
|
||||
public void digestWithFilter() throws Exception {
|
||||
MockHttpServletRequest postProcessedRequest = digest()
|
||||
.postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = digest().postProcessRequest(request);
|
||||
|
||||
assertThat(extractUser()).isEqualTo("user");
|
||||
}
|
||||
@@ -78,8 +78,7 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
@Test
|
||||
public void digestWithFilterCustomUsername() throws Exception {
|
||||
String username = "admin";
|
||||
MockHttpServletRequest postProcessedRequest = digest(username)
|
||||
.postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).postProcessRequest(request);
|
||||
|
||||
assertThat(extractUser()).isEqualTo(username);
|
||||
}
|
||||
@@ -88,8 +87,7 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
public void digestWithFilterCustomPassword() throws Exception {
|
||||
String username = "custom";
|
||||
password = "secret";
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).password(password)
|
||||
.postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).password(password).postProcessRequest(request);
|
||||
|
||||
assertThat(extractUser()).isEqualTo(username);
|
||||
}
|
||||
@@ -98,8 +96,8 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
public void digestWithFilterCustomRealm() throws Exception {
|
||||
String username = "admin";
|
||||
entryPoint.setRealmName("Custom");
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).realm(
|
||||
entryPoint.getRealmName()).postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).realm(entryPoint.getRealmName())
|
||||
.postProcessRequest(request);
|
||||
|
||||
assertThat(extractUser()).isEqualTo(username);
|
||||
}
|
||||
@@ -107,8 +105,7 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
@Test
|
||||
public void digestWithFilterFails() throws Exception {
|
||||
String username = "admin";
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).realm("Invalid")
|
||||
.postProcessRequest(request);
|
||||
MockHttpServletRequest postProcessedRequest = digest(username).realm("Invalid").postProcessRequest(request);
|
||||
|
||||
assertThat(extractUser()).isNull();
|
||||
}
|
||||
@@ -117,11 +114,11 @@ public class SecurityMockMvcRequestPostProcessorsDigestTests {
|
||||
filter.doFilter(request, new MockHttpServletResponse(), new MockFilterChain() {
|
||||
@Override
|
||||
public void doFilter(ServletRequest request, ServletResponse response) {
|
||||
Authentication authentication = SecurityContextHolder.getContext()
|
||||
.getAuthentication();
|
||||
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
|
||||
username = authentication == null ? null : authentication.getName();
|
||||
}
|
||||
});
|
||||
return username;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+14
-21
@@ -60,6 +60,7 @@ import static org.springframework.security.test.web.servlet.request.SecurityMock
|
||||
*/
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockMvcRequestPostProcessorsJwtTests {
|
||||
|
||||
@Captor
|
||||
private ArgumentCaptor<SecurityContext> contextCaptor;
|
||||
|
||||
@@ -70,6 +71,7 @@ public class SecurityMockMvcRequestPostProcessorsJwtTests {
|
||||
|
||||
@Mock
|
||||
private GrantedAuthority authority1;
|
||||
|
||||
@Mock
|
||||
private GrantedAuthority authority2;
|
||||
|
||||
@@ -95,8 +97,7 @@ public class SecurityMockMvcRequestPostProcessorsJwtTests {
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
any(HttpServletResponse.class));
|
||||
SecurityContext context = this.contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
JwtAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(JwtAuthenticationToken.class);
|
||||
JwtAuthenticationToken token = (JwtAuthenticationToken) context.getAuthentication();
|
||||
assertThat(token.getAuthorities()).isNotEmpty();
|
||||
assertThat(token.getToken()).isNotNull();
|
||||
@@ -112,57 +113,48 @@ public class SecurityMockMvcRequestPostProcessorsJwtTests {
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
any(HttpServletResponse.class));
|
||||
SecurityContext context = this.contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
JwtAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(JwtAuthenticationToken.class);
|
||||
JwtAuthenticationToken token = (JwtAuthenticationToken) context.getAuthentication();
|
||||
assertThat(token.getToken().getSubject()).isSameAs(name);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void jwtWhenProvidingCustomAuthoritiesThenProducesJwtAuthentication() {
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "ignored authorities"))
|
||||
.authorities(this.authority1, this.authority2)
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "ignored authorities")).authorities(this.authority1, this.authority2)
|
||||
.postProcessRequest(this.request);
|
||||
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
any(HttpServletResponse.class));
|
||||
SecurityContext context = this.contextCaptor.getValue();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(this.authority1, this.authority2);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(this.authority1,
|
||||
this.authority2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void jwtWhenProvidingScopedAuthoritiesThenProducesJwtAuthentication() {
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "scoped authorities"))
|
||||
.postProcessRequest(this.request);
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "scoped authorities")).postProcessRequest(this.request);
|
||||
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
any(HttpServletResponse.class));
|
||||
SecurityContext context = this.contextCaptor.getValue();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(new SimpleGrantedAuthority("SCOPE_scoped"),
|
||||
new SimpleGrantedAuthority("SCOPE_authorities"));
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(
|
||||
new SimpleGrantedAuthority("SCOPE_scoped"), new SimpleGrantedAuthority("SCOPE_authorities"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void jwtWhenProvidingGrantedAuthoritiesThenProducesJwtAuthentication() {
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "ignored authorities"))
|
||||
.authorities(jwt -> Arrays.asList(this.authority1))
|
||||
jwt().jwt(jwt -> jwt.claim("scope", "ignored authorities")).authorities(jwt -> Arrays.asList(this.authority1))
|
||||
.postProcessRequest(this.request);
|
||||
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
any(HttpServletResponse.class));
|
||||
SecurityContext context = this.contextCaptor.getValue();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(this.authority1);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(this.authority1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void jwtWhenProvidingPreparedJwtThenUsesItForAuthentication() {
|
||||
Jwt originalToken = TestJwts.jwt()
|
||||
.header("header1", "value1")
|
||||
.subject("some_user")
|
||||
.build();
|
||||
Jwt originalToken = TestJwts.jwt().header("header1", "value1").subject("some_user").build();
|
||||
jwt().jwt(originalToken).postProcessRequest(this.request);
|
||||
|
||||
verify(this.repository).saveContext(this.contextCaptor.capture(), eq(this.request),
|
||||
@@ -173,4 +165,5 @@ public class SecurityMockMvcRequestPostProcessorsJwtTests {
|
||||
assertThat(retrievedToken.getToken().getTokenValue()).isEqualTo("token");
|
||||
assertThat(retrievedToken.getToken().getHeaders().get("header1")).isEqualTo("value1");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+28
-31
@@ -69,6 +69,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
|
||||
@@ -89,19 +90,15 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
TestSecurityContextHolder.clearContext();
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsingDefaultsThenException()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenUsingDefaultsThenException() throws Exception {
|
||||
|
||||
assertThatCode(() -> oauth2Client().postProcessRequest(new MockHttpServletRequest()))
|
||||
.isInstanceOf(IllegalArgumentException.class)
|
||||
.hasMessageContaining("ClientRegistration");
|
||||
.isInstanceOf(IllegalArgumentException.class).hasMessageContaining("ClientRegistration");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsingDefaultsThenProducesDefaultAuthorizedClient()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenUsingDefaultsThenProducesDefaultAuthorizedClient() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/access-token").with(oauth2Client("registration-id")))
|
||||
.andExpect(content().string("access-token"));
|
||||
@@ -110,19 +107,16 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenClientRegistrationThenUses()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenClientRegistrationThenUses() throws Exception {
|
||||
|
||||
ClientRegistration clientRegistration = clientRegistration()
|
||||
.registrationId("registration-id").clientId("client-id").build();
|
||||
this.mvc.perform(get("/client-id")
|
||||
.with(oauth2Client().clientRegistration(clientRegistration)))
|
||||
ClientRegistration clientRegistration = clientRegistration().registrationId("registration-id")
|
||||
.clientId("client-id").build();
|
||||
this.mvc.perform(get("/client-id").with(oauth2Client().clientRegistration(clientRegistration)))
|
||||
.andExpect(content().string("client-id"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenClientRegistrationConsumerThenUses()
|
||||
throws Exception {
|
||||
public void oauth2ClientWhenClientRegistrationConsumerThenUses() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/client-id")
|
||||
.with(oauth2Client("registration-id").clientRegistration(c -> c.clientId("client-id"))))
|
||||
@@ -131,38 +125,35 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenPrincipalNameThenUses() throws Exception {
|
||||
this.mvc.perform(get("/principal-name")
|
||||
.with(oauth2Client("registration-id").principalName("test-subject")))
|
||||
this.mvc.perform(get("/principal-name").with(oauth2Client("registration-id").principalName("test-subject")))
|
||||
.andExpect(content().string("test-subject"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenAccessTokenThenUses() throws Exception {
|
||||
OAuth2AccessToken accessToken = noScopes();
|
||||
this.mvc.perform(get("/access-token")
|
||||
.with(oauth2Client("registration-id").accessToken(accessToken)))
|
||||
this.mvc.perform(get("/access-token").with(oauth2Client("registration-id").accessToken(accessToken)))
|
||||
.andExpect(content().string("no-scopes"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2ClientWhenUsedOnceThenDoesNotAffectRemainingTests() throws Exception {
|
||||
this.mvc.perform(get("/client-id")
|
||||
.with(oauth2Client("registration-id")))
|
||||
this.mvc.perform(get("/client-id").with(oauth2Client("registration-id")))
|
||||
.andExpect(content().string("test-client"));
|
||||
|
||||
OAuth2AuthorizedClient client = new OAuth2AuthorizedClient(clientRegistration().build(), "sub", noScopes());
|
||||
OAuth2AuthorizedClientRepository repository = this.context.getBean(OAuth2AuthorizedClientRepository.class);
|
||||
when(repository.loadAuthorizedClient(eq("registration-id"), any(Authentication.class), any(HttpServletRequest.class)))
|
||||
.thenReturn(client);
|
||||
this.mvc.perform(get("/client-id"))
|
||||
.andExpect(content().string("client-id"));
|
||||
verify(repository).loadAuthorizedClient(
|
||||
eq("registration-id"), any(Authentication.class), any(HttpServletRequest.class));
|
||||
when(repository.loadAuthorizedClient(eq("registration-id"), any(Authentication.class),
|
||||
any(HttpServletRequest.class))).thenReturn(client);
|
||||
this.mvc.perform(get("/client-id")).andExpect(content().string("client-id"));
|
||||
verify(repository).loadAuthorizedClient(eq("registration-id"), any(Authentication.class),
|
||||
any(HttpServletRequest.class));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class OAuth2ClientConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -179,7 +170,6 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
return mock(ClientRegistrationRepository.class);
|
||||
}
|
||||
|
||||
|
||||
@Bean
|
||||
OAuth2AuthorizedClientRepository authorizedClientRepository() {
|
||||
return mock(OAuth2AuthorizedClientRepository.class);
|
||||
@@ -187,20 +177,27 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2ClientTests {
|
||||
|
||||
@RestController
|
||||
static class PrincipalController {
|
||||
|
||||
@GetMapping("/access-token")
|
||||
String accessToken(@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
String accessToken(
|
||||
@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
return authorizedClient.getAccessToken().getTokenValue();
|
||||
}
|
||||
|
||||
@GetMapping("/principal-name")
|
||||
String principalName(@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
String principalName(
|
||||
@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
return authorizedClient.getPrincipalName();
|
||||
}
|
||||
|
||||
@GetMapping("/client-id")
|
||||
String clientId(@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
String clientId(
|
||||
@RegisteredOAuth2AuthorizedClient("registration-id") OAuth2AuthorizedClient authorizedClient) {
|
||||
return authorizedClient.getClientRegistration().getClientId();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+31
-44
@@ -69,6 +69,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcRequestPostProcessorsOAuth2LoginTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
|
||||
@@ -85,86 +86,69 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2LoginTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthentication()
|
||||
throws Exception {
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthentication() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/name").with(oauth2Login()))
|
||||
.andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/id-token/name").with(oauth2Login()))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/name").with(oauth2Login())).andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/id-token/name").with(oauth2Login())).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient()
|
||||
throws Exception {
|
||||
public void oauth2LoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/client-id").with(oauth2Login()))
|
||||
.andExpect(content().string("test-client"));
|
||||
this.mvc.perform(get("/client-id").with(oauth2Login())).andExpect(content().string("test-client"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenAuthoritiesSpecifiedThenGrantsAccess() throws Exception {
|
||||
this.mvc.perform(get("/admin/scopes")
|
||||
.with(oauth2Login().authorities(new SimpleGrantedAuthority("SCOPE_admin"))))
|
||||
this.mvc.perform(
|
||||
get("/admin/scopes").with(oauth2Login().authorities(new SimpleGrantedAuthority("SCOPE_admin"))))
|
||||
.andExpect(content().string("[\"SCOPE_admin\"]"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenAttributeSpecifiedThenUserHasAttribute() throws Exception {
|
||||
this.mvc.perform(get("/attributes/iss")
|
||||
.with(oauth2Login().attributes(a -> a.put("iss", "https://idp.example.org"))))
|
||||
this.mvc.perform(
|
||||
get("/attributes/iss").with(oauth2Login().attributes(a -> a.put("iss", "https://idp.example.org"))))
|
||||
.andExpect(content().string("https://idp.example.org"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenNameSpecifiedThenUserHasName() throws Exception {
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(
|
||||
AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("custom-attribute", "test-subject"),
|
||||
"custom-attribute");
|
||||
this.mvc.perform(get("/attributes/custom-attribute")
|
||||
.with(oauth2Login().oauth2User(oauth2User)))
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("custom-attribute", "test-subject"), "custom-attribute");
|
||||
this.mvc.perform(get("/attributes/custom-attribute").with(oauth2Login().oauth2User(oauth2User)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
|
||||
this.mvc.perform(get("/name")
|
||||
.with(oauth2Login().oauth2User(oauth2User)))
|
||||
this.mvc.perform(get("/name").with(oauth2Login().oauth2User(oauth2User)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
|
||||
this.mvc.perform(get("/client-name")
|
||||
.with(oauth2Login().oauth2User(oauth2User)))
|
||||
this.mvc.perform(get("/client-name").with(oauth2Login().oauth2User(oauth2User)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenClientRegistrationSpecifiedThenUses() throws Exception {
|
||||
this.mvc.perform(get("/client-id")
|
||||
.with(oauth2Login().clientRegistration(clientRegistration().build())))
|
||||
this.mvc.perform(get("/client-id").with(oauth2Login().clientRegistration(clientRegistration().build())))
|
||||
.andExpect(content().string("client-id"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oauth2LoginWhenOAuth2UserSpecifiedThenLastCalledTakesPrecedence() throws Exception {
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(
|
||||
AuthorityUtils.createAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("username", "user"),
|
||||
"username");
|
||||
OAuth2User oauth2User = new DefaultOAuth2User(AuthorityUtils.createAuthorityList("SCOPE_read"),
|
||||
Collections.singletonMap("username", "user"), "username");
|
||||
|
||||
this.mvc.perform(get("/attributes/sub")
|
||||
.with(oauth2Login()
|
||||
.attributes(a -> a.put("sub", "bar"))
|
||||
.oauth2User(oauth2User)))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(content().string("no-attribute"));
|
||||
this.mvc.perform(get("/attributes/sub")
|
||||
.with(oauth2Login()
|
||||
.oauth2User(oauth2User)
|
||||
.attributes(a -> a.put("sub", "bar"))))
|
||||
this.mvc.perform(
|
||||
get("/attributes/sub").with(oauth2Login().attributes(a -> a.put("sub", "bar")).oauth2User(oauth2User)))
|
||||
.andExpect(status().isOk()).andExpect(content().string("no-attribute"));
|
||||
this.mvc.perform(
|
||||
get("/attributes/sub").with(oauth2Login().oauth2User(oauth2User).attributes(a -> a.put("sub", "bar"))))
|
||||
.andExpect(content().string("bar"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class OAuth2LoginConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -188,6 +172,7 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2LoginTests {
|
||||
|
||||
@RestController
|
||||
static class PrincipalController {
|
||||
|
||||
@GetMapping("/name")
|
||||
String name(@AuthenticationPrincipal OAuth2User oauth2User) {
|
||||
return oauth2User.getName();
|
||||
@@ -204,8 +189,8 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2LoginTests {
|
||||
}
|
||||
|
||||
@GetMapping("/attributes/{attribute}")
|
||||
String attributes(
|
||||
@AuthenticationPrincipal OAuth2User oauth2User, @PathVariable("attribute") String attribute) {
|
||||
String attributes(@AuthenticationPrincipal OAuth2User oauth2User,
|
||||
@PathVariable("attribute") String attribute) {
|
||||
|
||||
return Optional.ofNullable((String) oauth2User.getAttribute(attribute)).orElse("no-attribute");
|
||||
}
|
||||
@@ -214,9 +199,11 @@ public class SecurityMockMvcRequestPostProcessorsOAuth2LoginTests {
|
||||
List<String> scopes(
|
||||
@AuthenticationPrincipal(expression = "authorities") Collection<GrantedAuthority> authorities) {
|
||||
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority)
|
||||
.collect(Collectors.toList());
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+25
-42
@@ -70,6 +70,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcRequestPostProcessorsOidcLoginTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
|
||||
@@ -91,86 +92,66 @@ public class SecurityMockMvcRequestPostProcessorsOidcLoginTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthentication()
|
||||
throws Exception {
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthentication() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/name").with(oidcLogin()))
|
||||
.andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/id-token/name").with(oidcLogin()))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/name").with(oidcLogin())).andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/id-token/name").with(oidcLogin())).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient()
|
||||
throws Exception {
|
||||
public void oidcLoginWhenUsingDefaultsThenProducesDefaultAuthorizedClient() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/access-token").with(oidcLogin()))
|
||||
.andExpect(content().string("access-token"));
|
||||
this.mvc.perform(get("/access-token").with(oidcLogin())).andExpect(content().string("access-token"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenAuthoritiesSpecifiedThenGrantsAccess() throws Exception {
|
||||
this.mvc.perform(get("/admin/scopes")
|
||||
.with(oidcLogin().authorities(new SimpleGrantedAuthority("SCOPE_admin"))))
|
||||
this.mvc.perform(get("/admin/scopes").with(oidcLogin().authorities(new SimpleGrantedAuthority("SCOPE_admin"))))
|
||||
.andExpect(content().string("[\"SCOPE_admin\"]"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenIdTokenSpecifiedThenUserHasClaims() throws Exception {
|
||||
this.mvc.perform(get("/id-token/iss")
|
||||
.with(oidcLogin().idToken(i -> i.issuer("https://idp.example.org"))))
|
||||
this.mvc.perform(get("/id-token/iss").with(oidcLogin().idToken(i -> i.issuer("https://idp.example.org"))))
|
||||
.andExpect(content().string("https://idp.example.org"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenUserInfoSpecifiedThenUserHasClaims() throws Exception {
|
||||
this.mvc.perform(get("/user-info/email")
|
||||
.with(oidcLogin().userInfoToken(u -> u.email("email@email"))))
|
||||
this.mvc.perform(get("/user-info/email").with(oidcLogin().userInfoToken(u -> u.email("email@email"))))
|
||||
.andExpect(content().string("email@email"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void oidcLoginWhenNameSpecifiedThenUserHasName() throws Exception {
|
||||
OidcUser oidcUser = new DefaultOidcUser(
|
||||
AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
OidcUser oidcUser = new DefaultOidcUser(AuthorityUtils.commaSeparatedStringToAuthorityList("SCOPE_read"),
|
||||
OidcIdToken.withTokenValue("id-token").claim("custom-attribute", "test-subject").build(),
|
||||
"custom-attribute");
|
||||
|
||||
this.mvc.perform(get("/id-token/custom-attribute")
|
||||
.with(oidcLogin().oidcUser(oidcUser)))
|
||||
this.mvc.perform(get("/id-token/custom-attribute").with(oidcLogin().oidcUser(oidcUser)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
|
||||
this.mvc.perform(get("/name")
|
||||
.with(oidcLogin().oidcUser(oidcUser)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
this.mvc.perform(get("/name").with(oidcLogin().oidcUser(oidcUser))).andExpect(content().string("test-subject"));
|
||||
|
||||
this.mvc.perform(get("/client-name")
|
||||
.with(oidcLogin().oidcUser(oidcUser)))
|
||||
this.mvc.perform(get("/client-name").with(oidcLogin().oidcUser(oidcUser)))
|
||||
.andExpect(content().string("test-subject"));
|
||||
}
|
||||
|
||||
// gh-7794
|
||||
@Test
|
||||
public void oidcLoginWhenOidcUserSpecifiedThenLastCalledTakesPrecedence() throws Exception {
|
||||
OidcUser oidcUser = new DefaultOidcUser(
|
||||
AuthorityUtils.createAuthorityList("SCOPE_read"), idToken().build());
|
||||
OidcUser oidcUser = new DefaultOidcUser(AuthorityUtils.createAuthorityList("SCOPE_read"), idToken().build());
|
||||
|
||||
this.mvc.perform(get("/id-token/sub")
|
||||
.with(oidcLogin()
|
||||
.idToken(i -> i.subject("foo"))
|
||||
.oidcUser(oidcUser)))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(content().string("subject"));
|
||||
this.mvc.perform(get("/id-token/sub")
|
||||
.with(oidcLogin()
|
||||
.oidcUser(oidcUser)
|
||||
.idToken(i -> i.subject("bar"))))
|
||||
this.mvc.perform(get("/id-token/sub").with(oidcLogin().idToken(i -> i.subject("foo")).oidcUser(oidcUser)))
|
||||
.andExpect(status().isOk()).andExpect(content().string("subject"));
|
||||
this.mvc.perform(get("/id-token/sub").with(oidcLogin().oidcUser(oidcUser).idToken(i -> i.subject("bar"))))
|
||||
.andExpect(content().string("bar"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class OAuth2LoginConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -188,7 +169,6 @@ public class SecurityMockMvcRequestPostProcessorsOidcLoginTests {
|
||||
return mock(ClientRegistrationRepository.class);
|
||||
}
|
||||
|
||||
|
||||
@Bean
|
||||
OAuth2AuthorizedClientRepository oAuth2AuthorizedClientRepository() {
|
||||
return mock(OAuth2AuthorizedClientRepository.class);
|
||||
@@ -196,6 +176,7 @@ public class SecurityMockMvcRequestPostProcessorsOidcLoginTests {
|
||||
|
||||
@RestController
|
||||
static class PrincipalController {
|
||||
|
||||
@GetMapping("/name")
|
||||
String name(@AuthenticationPrincipal OidcUser oidcUser) {
|
||||
return oidcUser.getName();
|
||||
@@ -222,11 +203,13 @@ public class SecurityMockMvcRequestPostProcessorsOidcLoginTests {
|
||||
}
|
||||
|
||||
@GetMapping("/admin/scopes")
|
||||
List<String> scopes(@AuthenticationPrincipal(expression = "authorities")
|
||||
Collection<GrantedAuthority> authorities) {
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority)
|
||||
.collect(Collectors.toList());
|
||||
List<String> scopes(
|
||||
@AuthenticationPrincipal(expression = "authorities") Collection<GrantedAuthority> authorities) {
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+20
-24
@@ -64,6 +64,7 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@ContextConfiguration
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext context;
|
||||
|
||||
@@ -80,19 +81,16 @@ public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void opaqueTokenWhenUsingDefaultsThenProducesDefaultAuthentication()
|
||||
throws Exception {
|
||||
public void opaqueTokenWhenUsingDefaultsThenProducesDefaultAuthentication() throws Exception {
|
||||
|
||||
this.mvc.perform(get("/name").with(opaqueToken()))
|
||||
.andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/scopes").with(opaqueToken()))
|
||||
.andExpect(status().isForbidden());
|
||||
this.mvc.perform(get("/name").with(opaqueToken())).andExpect(content().string("user"));
|
||||
this.mvc.perform(get("/admin/scopes").with(opaqueToken())).andExpect(status().isForbidden());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void opaqueTokenWhenAttributeSpecifiedThenUserHasAttribute() throws Exception {
|
||||
this.mvc.perform(get("/opaque-token/iss")
|
||||
.with(opaqueToken().attributes(a -> a.put("iss", "https://idp.example.org"))))
|
||||
this.mvc.perform(
|
||||
get("/opaque-token/iss").with(opaqueToken().attributes(a -> a.put("iss", "https://idp.example.org"))))
|
||||
.andExpect(content().string("https://idp.example.org"));
|
||||
}
|
||||
|
||||
@@ -103,8 +101,7 @@ public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
when(principal.getName()).thenReturn("ben");
|
||||
when(principal.getAuthorities()).thenReturn(authorities);
|
||||
|
||||
this.mvc.perform(get("/name").with(opaqueToken().principal(principal)))
|
||||
.andExpect(content().string("ben"));
|
||||
this.mvc.perform(get("/name").with(opaqueToken().principal(principal))).andExpect(content().string("ben"));
|
||||
}
|
||||
|
||||
// gh-7800
|
||||
@@ -112,22 +109,18 @@ public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
public void opaqueTokenWhenPrincipalSpecifiedThenLastCalledTakesPrecedence() throws Exception {
|
||||
OAuth2AuthenticatedPrincipal principal = active(a -> a.put("scope", "user"));
|
||||
|
||||
this.mvc.perform(get("/opaque-token/sub")
|
||||
.with(opaqueToken()
|
||||
.attributes(a -> a.put("sub", "foo"))
|
||||
.principal(principal)))
|
||||
.andExpect(status().isOk())
|
||||
.andExpect(content().string((String) principal.getAttribute("sub")));
|
||||
this.mvc.perform(get("/opaque-token/sub")
|
||||
.with(opaqueToken()
|
||||
.principal(principal)
|
||||
.attributes(a -> a.put("sub", "bar"))))
|
||||
this.mvc.perform(
|
||||
get("/opaque-token/sub").with(opaqueToken().attributes(a -> a.put("sub", "foo")).principal(principal)))
|
||||
.andExpect(status().isOk()).andExpect(content().string((String) principal.getAttribute("sub")));
|
||||
this.mvc.perform(
|
||||
get("/opaque-token/sub").with(opaqueToken().principal(principal).attributes(a -> a.put("sub", "bar"))))
|
||||
.andExpect(content().string("bar"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class OAuth2LoginConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Override
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
// @formatter:off
|
||||
@@ -144,6 +137,7 @@ public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
|
||||
@RestController
|
||||
static class PrincipalController {
|
||||
|
||||
@GetMapping("/name")
|
||||
String name(@AuthenticationPrincipal OAuth2AuthenticatedPrincipal principal) {
|
||||
return principal.getName();
|
||||
@@ -157,12 +151,14 @@ public class SecurityMockMvcRequestPostProcessorsOpaqueTokenTests {
|
||||
}
|
||||
|
||||
@GetMapping("/admin/scopes")
|
||||
List<String> scopes(@AuthenticationPrincipal(expression = "authorities")
|
||||
Collection<GrantedAuthority> authorities) {
|
||||
List<String> scopes(
|
||||
@AuthenticationPrincipal(expression = "authorities") Collection<GrantedAuthority> authorities) {
|
||||
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority)
|
||||
.collect(Collectors.toList());
|
||||
return authorities.stream().map(GrantedAuthority::getAuthority).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+6
-3
@@ -43,10 +43,13 @@ import org.springframework.security.web.context.SecurityContextRepository;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareOnlyThisForTest(WebTestUtils.class)
|
||||
@PowerMockIgnore({"javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*"})
|
||||
@PowerMockIgnore({ "javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*",
|
||||
"javax.xml.parsers.*" })
|
||||
public class SecurityMockMvcRequestPostProcessorsSecurityContextTests {
|
||||
|
||||
@Captor
|
||||
private ArgumentCaptor<SecurityContext> contextCaptor;
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository repository;
|
||||
|
||||
@@ -70,8 +73,7 @@ public class SecurityMockMvcRequestPostProcessorsSecurityContextTests {
|
||||
public void userDetails() {
|
||||
securityContext(expectedContext).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat(context).isSameAs(this.expectedContext);
|
||||
}
|
||||
@@ -80,4 +82,5 @@ public class SecurityMockMvcRequestPostProcessorsSecurityContextTests {
|
||||
spy(WebTestUtils.class);
|
||||
when(WebTestUtils.getSecurityContextRepository(request)).thenReturn(repository);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+5
-2
@@ -57,8 +57,7 @@ public class SecurityMockMvcRequestPostProcessorsTestSecurityContextStatelessTes
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.addFilters(springSecurityFilterChain)
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).addFilters(springSecurityFilterChain)
|
||||
.defaultRequest(get("/").with(testSecurityContext())).build();
|
||||
}
|
||||
|
||||
@@ -92,10 +91,14 @@ public class SecurityMockMvcRequestPostProcessorsTestSecurityContextStatelessTes
|
||||
|
||||
@RestController
|
||||
static class Controller {
|
||||
|
||||
@RequestMapping
|
||||
public String hello() {
|
||||
return "Hello";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+6
-3
@@ -40,10 +40,13 @@ import org.springframework.security.web.context.SecurityContextRepository;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareOnlyThisForTest(WebTestUtils.class)
|
||||
@PowerMockIgnore({"javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*"})
|
||||
@PowerMockIgnore({ "javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*",
|
||||
"javax.xml.parsers.*" })
|
||||
public class SecurityMockMvcRequestPostProcessorsTestSecurityContextTests {
|
||||
|
||||
@Mock
|
||||
private SecurityContext context;
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository repository;
|
||||
|
||||
@@ -66,8 +69,7 @@ public class SecurityMockMvcRequestPostProcessorsTestSecurityContextTests {
|
||||
|
||||
testSecurityContext().postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(eq(context), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(eq(context), eq(request), any(HttpServletResponse.class));
|
||||
}
|
||||
|
||||
// Ensure it does not fail if TestSecurityContextHolder is not initialized
|
||||
@@ -83,4 +85,5 @@ public class SecurityMockMvcRequestPostProcessorsTestSecurityContextTests {
|
||||
spy(WebTestUtils.class);
|
||||
when(WebTestUtils.getSecurityContextRepository(request)).thenReturn(repository);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-5
@@ -45,10 +45,13 @@ import org.springframework.security.web.context.SecurityContextRepository;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareOnlyThisForTest(WebTestUtils.class)
|
||||
@PowerMockIgnore({"javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*"})
|
||||
@PowerMockIgnore({ "javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*",
|
||||
"javax.xml.parsers.*" })
|
||||
public class SecurityMockMvcRequestPostProcessorsUserDetailsTests {
|
||||
|
||||
@Captor
|
||||
private ArgumentCaptor<SecurityContext> contextCaptor;
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository repository;
|
||||
|
||||
@@ -72,11 +75,9 @@ public class SecurityMockMvcRequestPostProcessorsUserDetailsTests {
|
||||
public void userDetails() {
|
||||
user(userDetails).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getPrincipal()).isSameAs(userDetails);
|
||||
}
|
||||
|
||||
@@ -84,4 +85,5 @@ public class SecurityMockMvcRequestPostProcessorsUserDetailsTests {
|
||||
spy(WebTestUtils.class);
|
||||
when(WebTestUtils.getSecurityContextRepository(request)).thenReturn(repository);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+21
-25
@@ -48,10 +48,13 @@ import org.springframework.security.web.context.SecurityContextRepository;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PrepareOnlyThisForTest(WebTestUtils.class)
|
||||
@PowerMockIgnore({"javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*", "javax.xml.parsers.*"})
|
||||
@PowerMockIgnore({ "javax.security.auth.*", "org.w3c.dom.*", "org.xml.sax.*", "org.apache.xerces.*",
|
||||
"javax.xml.parsers.*" })
|
||||
public class SecurityMockMvcRequestPostProcessorsUserTests {
|
||||
|
||||
@Captor
|
||||
private ArgumentCaptor<SecurityContext> contextCaptor;
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository repository;
|
||||
|
||||
@@ -59,6 +62,7 @@ public class SecurityMockMvcRequestPostProcessorsUserTests {
|
||||
|
||||
@Mock
|
||||
private GrantedAuthority authority1;
|
||||
|
||||
@Mock
|
||||
private GrantedAuthority authority2;
|
||||
|
||||
@@ -79,33 +83,27 @@ public class SecurityMockMvcRequestPostProcessorsUserTests {
|
||||
|
||||
user(username).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getName()).isEqualTo(username);
|
||||
assertThat(context.getAuthentication().getCredentials()).isEqualTo("password");
|
||||
assertThat(context.getAuthentication().getAuthorities()).extracting("authority")
|
||||
.containsOnly("ROLE_USER");
|
||||
assertThat(context.getAuthentication().getAuthorities()).extracting("authority").containsOnly("ROLE_USER");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void userWithCustom() {
|
||||
String username = "customuser";
|
||||
|
||||
user(username).roles("CUSTOM", "ADMIN").password("newpass")
|
||||
.postProcessRequest(request);
|
||||
user(username).roles("CUSTOM", "ADMIN").password("newpass").postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat(context.getAuthentication()).isInstanceOf(
|
||||
UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication()).isInstanceOf(UsernamePasswordAuthenticationToken.class);
|
||||
assertThat(context.getAuthentication().getName()).isEqualTo(username);
|
||||
assertThat(context.getAuthentication().getCredentials()).isEqualTo("newpass");
|
||||
assertThat(context.getAuthentication().getAuthorities()).extracting("authority")
|
||||
.containsOnly("ROLE_CUSTOM", "ROLE_ADMIN");
|
||||
assertThat(context.getAuthentication().getAuthorities()).extracting("authority").containsOnly("ROLE_CUSTOM",
|
||||
"ROLE_ADMIN");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -114,11 +112,10 @@ public class SecurityMockMvcRequestPostProcessorsUserTests {
|
||||
|
||||
user(username).authorities(authority1, authority2).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(authority1, authority2);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(authority1,
|
||||
authority2);
|
||||
}
|
||||
|
||||
@Test(expected = IllegalArgumentException.class)
|
||||
@@ -130,18 +127,17 @@ public class SecurityMockMvcRequestPostProcessorsUserTests {
|
||||
public void userCustomAuthoritiesList() {
|
||||
String username = "customuser";
|
||||
|
||||
user(username).authorities(Arrays.asList(authority1, authority2))
|
||||
.postProcessRequest(request);
|
||||
user(username).authorities(Arrays.asList(authority1, authority2)).postProcessRequest(request);
|
||||
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request),
|
||||
any(HttpServletResponse.class));
|
||||
verify(repository).saveContext(contextCaptor.capture(), eq(request), any(HttpServletResponse.class));
|
||||
SecurityContext context = contextCaptor.getValue();
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities())
|
||||
.containsOnly(authority1, authority2);
|
||||
assertThat((List<GrantedAuthority>) context.getAuthentication().getAuthorities()).containsOnly(authority1,
|
||||
authority2);
|
||||
}
|
||||
|
||||
private void mockWebTestUtils() {
|
||||
spy(WebTestUtils.class);
|
||||
when(WebTestUtils.getSecurityContextRepository(request)).thenReturn(repository);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+2
@@ -106,5 +106,7 @@ public class Gh3409Tests {
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+9
-6
@@ -47,6 +47,7 @@ import static org.springframework.security.test.web.servlet.setup.SecurityMockMv
|
||||
@ContextConfiguration(classes = SecurityMockMvcResultMatchersTests.Config.class)
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcResultMatchersTests {
|
||||
|
||||
@Autowired
|
||||
private WebApplicationContext context;
|
||||
|
||||
@@ -64,16 +65,14 @@ public class SecurityMockMvcResultMatchersTests {
|
||||
|
||||
@Test
|
||||
public void withAuthenticationWhenMatchesThenSuccess() throws Exception {
|
||||
this.mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(auth ->
|
||||
assertThat(auth).isInstanceOf(UsernamePasswordAuthenticationToken.class)));
|
||||
this.mockMvc.perform(formLogin()).andExpect(authenticated()
|
||||
.withAuthentication(auth -> assertThat(auth).isInstanceOf(UsernamePasswordAuthenticationToken.class)));
|
||||
}
|
||||
|
||||
@Test(expected = AssertionError.class)
|
||||
public void withAuthenticationWhenNotMatchesThenFails() throws Exception {
|
||||
this.mockMvc
|
||||
.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthentication(auth -> assertThat(auth.getName()).isEqualTo("notmatch")));
|
||||
this.mockMvc.perform(formLogin()).andExpect(
|
||||
authenticated().withAuthentication(auth -> assertThat(auth.getName()).isEqualTo("notmatch")));
|
||||
}
|
||||
|
||||
// SEC-2719
|
||||
@@ -110,10 +109,14 @@ public class SecurityMockMvcResultMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class Controller {
|
||||
|
||||
@RequestMapping("/")
|
||||
public String ok() {
|
||||
return "ok";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-4
@@ -49,6 +49,7 @@ import org.springframework.web.servlet.config.annotation.EnableWebMvc;
|
||||
@ContextConfiguration(classes = SecurityMockWithAuthoritiesMvcResultMatchersTests.Config.class)
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockWithAuthoritiesMvcResultMatchersTests {
|
||||
|
||||
@Autowired
|
||||
private WebApplicationContext context;
|
||||
|
||||
@@ -56,8 +57,7 @@ public class SecurityMockWithAuthoritiesMvcResultMatchersTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mockMvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity())
|
||||
.build();
|
||||
mockMvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity()).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -65,8 +65,7 @@ public class SecurityMockWithAuthoritiesMvcResultMatchersTests {
|
||||
List<SimpleGrantedAuthority> grantedAuthorities = new ArrayList<>();
|
||||
grantedAuthorities.add(new SimpleGrantedAuthority("ROLE_ADMIN"));
|
||||
grantedAuthorities.add(new SimpleGrantedAuthority("ROLE_SELLER"));
|
||||
mockMvc.perform(formLogin())
|
||||
.andExpect(authenticated().withAuthorities(grantedAuthorities));
|
||||
mockMvc.perform(formLogin()).andExpect(authenticated().withAuthorities(grantedAuthorities));
|
||||
}
|
||||
|
||||
@Test(expected = AssertionError.class)
|
||||
@@ -90,10 +89,14 @@ public class SecurityMockWithAuthoritiesMvcResultMatchersTests {
|
||||
|
||||
@RestController
|
||||
static class Controller {
|
||||
|
||||
@RequestMapping("/")
|
||||
public String ok() {
|
||||
return "ok";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+10
-6
@@ -36,14 +36,19 @@ import static org.mockito.Mockito.when;
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class SecurityMockMvcConfigurerTests {
|
||||
|
||||
@Mock
|
||||
private Filter filter;
|
||||
|
||||
@Mock
|
||||
private Filter beanFilter;
|
||||
|
||||
@Mock
|
||||
private ConfigurableMockMvcBuilder<?> builder;
|
||||
|
||||
@Mock
|
||||
private WebApplicationContext context;
|
||||
|
||||
@Mock
|
||||
private ServletContext servletContext;
|
||||
|
||||
@@ -61,8 +66,7 @@ public class SecurityMockMvcConfigurerTests {
|
||||
configurer.beforeMockMvcCreated(this.builder, this.context);
|
||||
|
||||
assertFilterAdded(this.filter);
|
||||
verify(this.servletContext).setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN,
|
||||
this.filter);
|
||||
verify(this.servletContext).setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN, this.filter);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -95,15 +99,15 @@ public class SecurityMockMvcConfigurerTests {
|
||||
}
|
||||
|
||||
private void assertFilterAdded(Filter filter) {
|
||||
ArgumentCaptor<SecurityMockMvcConfigurer.DelegateFilter> filterArg = ArgumentCaptor.forClass(
|
||||
SecurityMockMvcConfigurer.DelegateFilter.class);
|
||||
ArgumentCaptor<SecurityMockMvcConfigurer.DelegateFilter> filterArg = ArgumentCaptor
|
||||
.forClass(SecurityMockMvcConfigurer.DelegateFilter.class);
|
||||
verify(this.builder).addFilters(filterArg.capture());
|
||||
assertThat(filterArg.getValue().getDelegate()).isEqualTo(filter);
|
||||
}
|
||||
|
||||
private void returnFilterBean() {
|
||||
when(this.context.containsBean(anyString())).thenReturn(true);
|
||||
when(this.context.getBean(anyString(), eq(Filter.class)))
|
||||
.thenReturn(this.beanFilter);
|
||||
when(this.context.getBean(anyString(), eq(Filter.class))).thenReturn(this.beanFilter);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+16
-17
@@ -42,46 +42,45 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
|
||||
@RunWith(SpringRunner.class)
|
||||
@WebAppConfiguration
|
||||
public class SecurityMockMvcConfigurersTests {
|
||||
|
||||
@Autowired
|
||||
WebApplicationContext wac;
|
||||
|
||||
Filter noOpFilter = mock(Filter.class);
|
||||
|
||||
/**
|
||||
* Since noOpFilter is first does not continue the chain, security will not be invoked and the status should be OK
|
||||
*
|
||||
* Since noOpFilter is first does not continue the chain, security will not be invoked
|
||||
* and the status should be OK
|
||||
* @throws Exception
|
||||
*/
|
||||
@Test
|
||||
public void applySpringSecurityWhenAddFilterFirstThenFilterFirst() throws Exception {
|
||||
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(this.wac)
|
||||
.addFilters(this.noOpFilter)
|
||||
.apply(springSecurity())
|
||||
.build();
|
||||
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).addFilters(this.noOpFilter)
|
||||
.apply(springSecurity()).build();
|
||||
|
||||
mockMvc.perform(get("/"))
|
||||
.andExpect(status().isOk());
|
||||
mockMvc.perform(get("/")).andExpect(status().isOk());
|
||||
}
|
||||
|
||||
/**
|
||||
* Since noOpFilter is second security will be invoked and the status will be not OK. We know this because if noOpFilter
|
||||
* were first security would not be invoked sincet noOpFilter does not continue the FilterChain
|
||||
* Since noOpFilter is second security will be invoked and the status will be not OK.
|
||||
* We know this because if noOpFilter were first security would not be invoked sincet
|
||||
* noOpFilter does not continue the FilterChain
|
||||
* @throws Exception
|
||||
*/
|
||||
@Test
|
||||
public void applySpringSecurityWhenAddFilterSecondThenSecurityFirst() throws Exception {
|
||||
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(this.wac)
|
||||
.apply(springSecurity())
|
||||
.addFilters(this.noOpFilter)
|
||||
.build();
|
||||
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).apply(springSecurity())
|
||||
.addFilters(this.noOpFilter).build();
|
||||
|
||||
mockMvc.perform(get("/"))
|
||||
.andExpect(status().is4xxClientError());
|
||||
mockMvc.perform(get("/")).andExpect(status().is4xxClientError());
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@EnableWebMvc
|
||||
@EnableWebSecurity
|
||||
@Import(AuthenticationTestConfiguration.class)
|
||||
static class Config {}
|
||||
static class Config {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+2
@@ -83,5 +83,7 @@ public class CsrfShowcaseTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
-2
@@ -56,8 +56,8 @@ public class CustomCsrfShowcaseTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.defaultRequest(get("/").with(csrf())).apply(springSecurity()).build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).defaultRequest(get("/").with(csrf())).apply(springSecurity())
|
||||
.build();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -98,5 +98,7 @@ public class CustomCsrfShowcaseTests {
|
||||
repo.setParameterName("custom_csrf");
|
||||
return repo;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
-2
@@ -48,8 +48,8 @@ public class DefaultCsrfShowcaseTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.defaultRequest(get("/").with(csrf())).apply(springSecurity()).build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).defaultRequest(get("/").with(csrf())).apply(springSecurity())
|
||||
.build();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -78,5 +78,7 @@ public class DefaultCsrfShowcaseTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+9
-12
@@ -54,10 +54,8 @@ public class AuthenticationTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.apply(springSecurity())
|
||||
.defaultRequest(get("/").accept(MediaType.TEXT_HTML))
|
||||
.build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).apply(springSecurity())
|
||||
.defaultRequest(get("/").accept(MediaType.TEXT_HTML)).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -67,29 +65,26 @@ public class AuthenticationTests {
|
||||
|
||||
@Test
|
||||
public void httpBasicAuthenticationSuccess() throws Exception {
|
||||
mvc.perform(get("/secured/butnotfound").with(httpBasic("user", "password")))
|
||||
.andExpect(status().isNotFound())
|
||||
mvc.perform(get("/secured/butnotfound").with(httpBasic("user", "password"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticationSuccess() throws Exception {
|
||||
mvc.perform(formLogin()).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"))
|
||||
mvc.perform(formLogin()).andExpect(status().isFound()).andExpect(redirectedUrl("/"))
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticationFailed() throws Exception {
|
||||
mvc.perform(formLogin().user("user").password("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?error"))
|
||||
.andExpect(unauthenticated());
|
||||
mvc.perform(formLogin().user("user").password("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/login?error")).andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@EnableWebMvc
|
||||
static class Config extends WebSecurityConfigurerAdapter {
|
||||
|
||||
@Bean
|
||||
public UserDetailsService userDetailsService() {
|
||||
// @formatter:off
|
||||
@@ -97,5 +92,7 @@ public class AuthenticationTests {
|
||||
return new InMemoryUserDetailsManager(user);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-10
@@ -64,26 +64,21 @@ public class CustomConfigAuthenticationTests {
|
||||
|
||||
@Test
|
||||
public void authenticationSuccess() throws Exception {
|
||||
mvc.perform(
|
||||
formLogin("/authenticate").user("user", "user").password("pass",
|
||||
"password")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"))
|
||||
mvc.perform(formLogin("/authenticate").user("user", "user").password("pass", "password"))
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/"))
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void withUserSuccess() throws Exception {
|
||||
mvc.perform(get("/").with(user("user")))
|
||||
.andExpect(status().isNotFound())
|
||||
mvc.perform(get("/").with(user("user"))).andExpect(status().isNotFound())
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticationFailed() throws Exception {
|
||||
mvc.perform(
|
||||
formLogin("/authenticate").user("user", "notfound").password("pass",
|
||||
"invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/authenticate?error"))
|
||||
mvc.perform(formLogin("/authenticate").user("user", "notfound").password("pass", "invalid"))
|
||||
.andExpect(status().isFound()).andExpect(redirectedUrl("/authenticate?error"))
|
||||
.andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
@@ -122,5 +117,7 @@ public class CustomConfigAuthenticationTests {
|
||||
repo.setSpringSecurityContextKey("CUSTOM");
|
||||
return repo;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+6
-9
@@ -58,23 +58,18 @@ public class CustomLoginRequestBuilderAuthenticationTests {
|
||||
|
||||
@Test
|
||||
public void authenticationSuccess() throws Exception {
|
||||
mvc.perform(login())
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/"))
|
||||
mvc.perform(login()).andExpect(status().isFound()).andExpect(redirectedUrl("/"))
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void authenticationFailed() throws Exception {
|
||||
mvc.perform(login().user("notfound").password("invalid"))
|
||||
.andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/authenticate?error"))
|
||||
.andExpect(unauthenticated());
|
||||
mvc.perform(login().user("notfound").password("invalid")).andExpect(status().isFound())
|
||||
.andExpect(redirectedUrl("/authenticate?error")).andExpect(unauthenticated());
|
||||
}
|
||||
|
||||
static FormLoginRequestBuilder login() {
|
||||
return SecurityMockMvcRequestBuilders.formLogin("/authenticate")
|
||||
.userParameter("user").passwordParam("pass");
|
||||
return SecurityMockMvcRequestBuilders.formLogin("/authenticate").userParameter("user").passwordParam("pass");
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -102,5 +97,7 @@ public class CustomLoginRequestBuilderAuthenticationTests {
|
||||
return new InMemoryUserDetailsManager(user);
|
||||
}
|
||||
// @formatter:on
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+5
-4
@@ -49,15 +49,14 @@ public class DefaultfSecurityRequestsTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.defaultRequest(get("/").with(user("user").roles("ADMIN")))
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).defaultRequest(get("/").with(user("user").roles("ADMIN")))
|
||||
.apply(springSecurity()).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void requestProtectedUrlWithUser() throws Exception {
|
||||
mvc.perform(get("/"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -66,7 +65,7 @@ public class DefaultfSecurityRequestsTests {
|
||||
@Test
|
||||
public void requestProtectedUrlWithAdmin() throws Exception {
|
||||
mvc.perform(get("/admin"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -105,5 +104,7 @@ public class DefaultfSecurityRequestsTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+7
-6
@@ -63,7 +63,7 @@ public class SecurityRequestsTests {
|
||||
@Test
|
||||
public void requestProtectedUrlWithUser() throws Exception {
|
||||
mvc.perform(get("/").with(user("user")))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -72,7 +72,7 @@ public class SecurityRequestsTests {
|
||||
@Test
|
||||
public void requestProtectedUrlWithAdmin() throws Exception {
|
||||
mvc.perform(get("/admin").with(user("admin").roles("ADMIN")))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with admin
|
||||
.andExpect(authenticated().withUsername("admin"));
|
||||
@@ -82,7 +82,7 @@ public class SecurityRequestsTests {
|
||||
public void requestProtectedUrlWithUserDetails() throws Exception {
|
||||
UserDetails user = userDetailsService.loadUserByUsername("user");
|
||||
mvc.perform(get("/").with(user(user)))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withAuthenticationPrincipal(user));
|
||||
@@ -90,10 +90,9 @@ public class SecurityRequestsTests {
|
||||
|
||||
@Test
|
||||
public void requestProtectedUrlWithAuthentication() throws Exception {
|
||||
Authentication authentication = new TestingAuthenticationToken("test", "notused",
|
||||
"ROLE_USER");
|
||||
Authentication authentication = new TestingAuthenticationToken("test", "notused", "ROLE_USER");
|
||||
mvc.perform(get("/").with(authentication(authentication)))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withAuthentication(authentication));
|
||||
@@ -129,5 +128,7 @@ public class SecurityRequestsTests {
|
||||
public UserDetailsService userDetailsServiceBean() throws Exception {
|
||||
return super.userDetailsServiceBean();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+2
-1
@@ -28,6 +28,7 @@ import org.springframework.security.test.context.support.WithMockUser;
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Inherited
|
||||
@Documented
|
||||
@WithMockUser(value="rob", roles="ADMIN")
|
||||
@WithMockUser(value = "rob", roles = "ADMIN")
|
||||
public @interface WithAdminRob {
|
||||
|
||||
}
|
||||
|
||||
+6
-5
@@ -49,15 +49,14 @@ public class WithUserAuthenticationTests {
|
||||
|
||||
@Before
|
||||
public void setup() {
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context)
|
||||
.apply(SecurityMockMvcConfigurers.springSecurity()).build();
|
||||
mvc = MockMvcBuilders.webAppContextSetup(context).apply(SecurityMockMvcConfigurers.springSecurity()).build();
|
||||
}
|
||||
|
||||
@Test
|
||||
@WithMockUser
|
||||
public void requestProtectedUrlWithUser() throws Exception {
|
||||
mvc.perform(get("/"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -67,7 +66,7 @@ public class WithUserAuthenticationTests {
|
||||
@WithAdminRob
|
||||
public void requestProtectedUrlWithAdminRob() throws Exception {
|
||||
mvc.perform(get("/"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("rob").withRoles("ADMIN"));
|
||||
@@ -77,7 +76,7 @@ public class WithUserAuthenticationTests {
|
||||
@WithMockUser(roles = "ADMIN")
|
||||
public void requestProtectedUrlWithAdmin() throws Exception {
|
||||
mvc.perform(get("/admin"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user").withRoles("ADMIN"));
|
||||
@@ -107,5 +106,7 @@ public class WithUserAuthenticationTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+4
-2
@@ -58,7 +58,7 @@ public class WithUserClassLevelAuthenticationTests {
|
||||
@Test
|
||||
public void requestProtectedUrlWithUser() throws Exception {
|
||||
mvc.perform(get("/"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -67,7 +67,7 @@ public class WithUserClassLevelAuthenticationTests {
|
||||
@Test
|
||||
public void requestProtectedUrlWithAdmin() throws Exception {
|
||||
mvc.perform(get("/admin"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user").withRoles("ADMIN"));
|
||||
@@ -107,5 +107,7 @@ public class WithUserClassLevelAuthenticationTests {
|
||||
.withUser("user").password("password").roles("USER");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+4
-3
@@ -58,7 +58,7 @@ public class WithUserDetailsAuthenticationTests {
|
||||
@WithUserDetails
|
||||
public void requestProtectedUrlWithUser() throws Exception {
|
||||
mvc.perform(get("/"))
|
||||
// Ensure we got past Security
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(authenticated().withUsername("user"));
|
||||
@@ -71,8 +71,7 @@ public class WithUserDetailsAuthenticationTests {
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(
|
||||
authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
.andExpect(authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -106,5 +105,7 @@ public class WithUserDetailsAuthenticationTests {
|
||||
.withUser("admin").password("password").roles("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+4
-4
@@ -61,8 +61,7 @@ public class WithUserDetailsClassLevelAuthenticationTests {
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(
|
||||
authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
.andExpect(authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -71,8 +70,7 @@ public class WithUserDetailsClassLevelAuthenticationTests {
|
||||
// Ensure we got past Security
|
||||
.andExpect(status().isNotFound())
|
||||
// Ensure it appears we are authenticated with user
|
||||
.andExpect(
|
||||
authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
.andExpect(authenticated().withUsername("admin").withRoles("ADMIN", "USER"));
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -106,5 +104,7 @@ public class WithUserDetailsClassLevelAuthenticationTests {
|
||||
.withUser("admin").password("password").roles("USER", "ADMIN");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+23
-24
@@ -47,12 +47,15 @@ import static org.springframework.security.test.web.support.WebTestUtils.getSecu
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class WebTestUtilsTests {
|
||||
|
||||
@Mock
|
||||
private SecurityContextRepository contextRepo;
|
||||
|
||||
@Mock
|
||||
private CsrfTokenRepository csrfRepo;
|
||||
|
||||
private MockHttpServletRequest request;
|
||||
|
||||
private ConfigurableApplicationContext context;
|
||||
|
||||
@Before
|
||||
@@ -69,22 +72,19 @@ public class WebTestUtilsTests {
|
||||
|
||||
@Test
|
||||
public void getCsrfTokenRepositorytNoWac() {
|
||||
assertThat(getCsrfTokenRepository(this.request))
|
||||
.isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
assertThat(getCsrfTokenRepository(this.request)).isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getCsrfTokenRepositorytNoSecurity() {
|
||||
loadConfig(Config.class);
|
||||
assertThat(getCsrfTokenRepository(this.request))
|
||||
.isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
assertThat(getCsrfTokenRepository(this.request)).isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getCsrfTokenRepositorytSecurityNoCsrf() {
|
||||
loadConfig(SecurityNoCsrfConfig.class);
|
||||
assertThat(getCsrfTokenRepository(this.request))
|
||||
.isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
assertThat(getCsrfTokenRepository(this.request)).isInstanceOf(HttpSessionCsrfTokenRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -99,22 +99,19 @@ public class WebTestUtilsTests {
|
||||
|
||||
@Test
|
||||
public void getSecurityContextRepositoryNoWac() {
|
||||
assertThat(getSecurityContextRepository(this.request))
|
||||
.isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
assertThat(getSecurityContextRepository(this.request)).isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getSecurityContextRepositoryNoSecurity() {
|
||||
loadConfig(Config.class);
|
||||
assertThat(getSecurityContextRepository(this.request))
|
||||
.isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
assertThat(getSecurityContextRepository(this.request)).isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getSecurityContextRepositorySecurityNoCsrf() {
|
||||
loadConfig(SecurityNoCsrfConfig.class);
|
||||
assertThat(getSecurityContextRepository(this.request))
|
||||
.isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
assertThat(getSecurityContextRepository(this.request)).isInstanceOf(HttpSessionSecurityContextRepository.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -130,8 +127,7 @@ public class WebTestUtilsTests {
|
||||
public void findFilterNoMatchingFilters() {
|
||||
loadConfig(PartialSecurityConfig.class);
|
||||
|
||||
assertThat(WebTestUtils.findFilter(this.request,
|
||||
SecurityContextPersistenceFilter.class)).isNull();
|
||||
assertThat(WebTestUtils.findFilter(this.request, SecurityContextPersistenceFilter.class)).isNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -141,11 +137,9 @@ public class WebTestUtilsTests {
|
||||
CsrfFilter toFind = new CsrfFilter(new HttpSessionCsrfTokenRepository());
|
||||
FilterChainProxy springSecurityFilterChain = new FilterChainProxy(
|
||||
new DefaultSecurityFilterChain(AnyRequestMatcher.INSTANCE, toFind));
|
||||
this.request.getServletContext().setAttribute(
|
||||
BeanIds.SPRING_SECURITY_FILTER_CHAIN, springSecurityFilterChain);
|
||||
this.request.getServletContext().setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN, springSecurityFilterChain);
|
||||
|
||||
assertThat(WebTestUtils.findFilter(this.request, toFind.getClass()))
|
||||
.isEqualTo(toFind);
|
||||
assertThat(WebTestUtils.findFilter(this.request, toFind.getClass())).isEqualTo(toFind);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -155,11 +149,9 @@ public class WebTestUtilsTests {
|
||||
CsrfFilter toFind = new CsrfFilter(new HttpSessionCsrfTokenRepository());
|
||||
FilterChainProxy springSecurityFilterChain = new FilterChainProxy(
|
||||
new DefaultSecurityFilterChain(AnyRequestMatcher.INSTANCE, toFind));
|
||||
this.request.getServletContext().setAttribute(
|
||||
BeanIds.SPRING_SECURITY_FILTER_CHAIN, springSecurityFilterChain);
|
||||
this.request.getServletContext().setAttribute(BeanIds.SPRING_SECURITY_FILTER_CHAIN, springSecurityFilterChain);
|
||||
|
||||
assertThat(WebTestUtils.findFilter(this.request, toFind.getClass()))
|
||||
.isSameAs(toFind);
|
||||
assertThat(WebTestUtils.findFilter(this.request, toFind.getClass())).isSameAs(toFind);
|
||||
}
|
||||
|
||||
private void loadConfig(Class<?> config) {
|
||||
@@ -167,12 +159,13 @@ public class WebTestUtilsTests {
|
||||
context.register(config);
|
||||
context.refresh();
|
||||
this.context = context;
|
||||
this.request.getServletContext().setAttribute(
|
||||
WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, context);
|
||||
this.request.getServletContext().setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE,
|
||||
context);
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class Config {
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -182,10 +175,12 @@ public class WebTestUtilsTests {
|
||||
protected void configure(HttpSecurity http) throws Exception {
|
||||
http.csrf().disable();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class CustomSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
|
||||
static CsrfTokenRepository CSRF_REPO;
|
||||
static SecurityContextRepository CONTEXT_REPO;
|
||||
|
||||
@@ -200,6 +195,7 @@ public class WebTestUtilsTests {
|
||||
.securityContextRepository(CONTEXT_REPO);
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
@@ -212,14 +208,17 @@ public class WebTestUtilsTests {
|
||||
.antMatcher("/willnotmatchthis");
|
||||
// @formatter:on
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class NoSecurityConfig {
|
||||
|
||||
}
|
||||
|
||||
@EnableWebSecurity
|
||||
static class SecurityConfigWithDefaults extends WebSecurityConfigurerAdapter {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user