Skip to content

Commit f496ded

Browse files
committed
AuthorizationManager allows null Authentication
It is possible to have a null Authentication and so the AuthorizationManager APIs should allow for passing it in. Closes gh-17795
1 parent 583e668 commit f496ded

19 files changed

+58
-37
lines changed

config/src/main/kotlin/org/springframework/security/config/annotation/web/AuthorizeHttpRequestsDsl.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -235,13 +235,13 @@ class AuthorizeHttpRequestsDsl : AbstractRequestMatcherDsl {
235235
* Specify that URLs are allowed by anyone.
236236
*/
237237
val permitAll: AuthorizationManager<RequestAuthorizationContext> =
238-
AuthorizationManager { _: Supplier<Authentication>, _: RequestAuthorizationContext -> AuthorizationDecision(true) }
238+
AuthorizationManager { _: Supplier<Authentication?>, _: RequestAuthorizationContext -> AuthorizationDecision(true) }
239239

240240
/**
241241
* Specify that URLs are not allowed by anyone.
242242
*/
243243
val denyAll: AuthorizationManager<RequestAuthorizationContext> =
244-
AuthorizationManager { _: Supplier<Authentication>, _: RequestAuthorizationContext -> AuthorizationDecision(false) }
244+
AuthorizationManager { _: Supplier<Authentication?>, _: RequestAuthorizationContext -> AuthorizationDecision(false) }
245245

246246
/**
247247
* Specify that URLs are allowed by any authenticated user.

config/src/test/kotlin/org/springframework/security/config/annotation/web/AuthorizeHttpRequestsDslTests.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -193,7 +193,7 @@ class AuthorizeHttpRequestsDslTests {
193193
open class MvcMatcherPathVariablesConfig {
194194
@Bean
195195
open fun securityFilterChain(http: HttpSecurity): SecurityFilterChain {
196-
val access = AuthorizationManager { _: Supplier<Authentication>, context: RequestAuthorizationContext ->
196+
val access = AuthorizationManager { _: Supplier<Authentication?>, context: RequestAuthorizationContext ->
197197
AuthorizationDecision(context.variables["userName"] == "user")
198198
}
199199
http {

core/src/main/java/org/springframework/security/access/expression/AbstractSecurityExpressionHandler.java

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ public final void setExpressionParser(ExpressionParser expressionParser) {
7070
* suitable root object.
7171
*/
7272
@Override
73-
public final EvaluationContext createEvaluationContext(Authentication authentication, T invocation) {
73+
public final EvaluationContext createEvaluationContext(@Nullable Authentication authentication, T invocation) {
7474
SecurityExpressionOperations root = createSecurityExpressionRoot(authentication, invocation);
7575
StandardEvaluationContext ctx = createEvaluationContextInternal(authentication, invocation);
7676
if (this.beanResolver != null) {
@@ -91,7 +91,8 @@ public final EvaluationContext createEvaluationContext(Authentication authentica
9191
* @return A {@code StandardEvaluationContext} or potentially a custom subclass if
9292
* overridden.
9393
*/
94-
protected StandardEvaluationContext createEvaluationContextInternal(Authentication authentication, T invocation) {
94+
protected StandardEvaluationContext createEvaluationContextInternal(@Nullable Authentication authentication,
95+
T invocation) {
9596
return new StandardEvaluationContext();
9697
}
9798

@@ -102,8 +103,8 @@ protected StandardEvaluationContext createEvaluationContextInternal(Authenticati
102103
* @param invocation the invocation (filter, method, channel)
103104
* @return the object
104105
*/
105-
protected abstract SecurityExpressionOperations createSecurityExpressionRoot(Authentication authentication,
106-
T invocation);
106+
protected abstract SecurityExpressionOperations createSecurityExpressionRoot(
107+
@Nullable Authentication authentication, T invocation);
107108

108109
protected @Nullable RoleHierarchy getRoleHierarchy() {
109110
return this.roleHierarchy;

core/src/main/java/org/springframework/security/access/expression/SecurityExpressionHandler.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@
1818

1919
import java.util.function.Supplier;
2020

21+
import org.jspecify.annotations.Nullable;
22+
2123
import org.springframework.aop.framework.AopInfrastructureBean;
2224
import org.springframework.expression.EvaluationContext;
2325
import org.springframework.expression.ExpressionParser;
@@ -42,7 +44,7 @@ public interface SecurityExpressionHandler<T> extends AopInfrastructureBean {
4244
* Provides an evaluation context in which to evaluate security expressions for the
4345
* invocation type.
4446
*/
45-
EvaluationContext createEvaluationContext(Authentication authentication, T invocation);
47+
EvaluationContext createEvaluationContext(@Nullable Authentication authentication, T invocation);
4648

4749
/**
4850
* Provides an evaluation context in which to evaluate security expressions for the
@@ -55,7 +57,7 @@ public interface SecurityExpressionHandler<T> extends AopInfrastructureBean {
5557
* @return the {@link EvaluationContext} to use
5658
* @since 5.8
5759
*/
58-
default EvaluationContext createEvaluationContext(Supplier<Authentication> authentication, T invocation) {
60+
default EvaluationContext createEvaluationContext(Supplier<@Nullable Authentication> authentication, T invocation) {
5961
return createEvaluationContext(authentication.get(), invocation);
6062
}
6163

core/src/main/java/org/springframework/security/access/expression/SecurityExpressionRoot.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ public abstract class SecurityExpressionRoot implements SecurityExpressionOperat
7878
* Creates a new instance
7979
* @param authentication the {@link Authentication} to use. Cannot be null.
8080
*/
81-
public SecurityExpressionRoot(Authentication authentication) {
81+
public SecurityExpressionRoot(@Nullable Authentication authentication) {
8282
this(() -> authentication);
8383
}
8484

@@ -89,7 +89,7 @@ public SecurityExpressionRoot(Authentication authentication) {
8989
* Cannot be null.
9090
* @since 5.8
9191
*/
92-
public SecurityExpressionRoot(Supplier<Authentication> authentication) {
92+
public SecurityExpressionRoot(Supplier<@Nullable Authentication> authentication) {
9393
this.authentication = SingletonSupplier.of(() -> {
9494
Authentication value = authentication.get();
9595
Assert.notNull(value, "Authentication object cannot be null");

core/src/main/java/org/springframework/security/access/expression/method/DefaultMethodSecurityExpressionHandler.java

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -79,12 +79,14 @@ public DefaultMethodSecurityExpressionHandler() {
7979
* implementation.
8080
*/
8181
@Override
82-
public StandardEvaluationContext createEvaluationContextInternal(Authentication auth, MethodInvocation mi) {
82+
public StandardEvaluationContext createEvaluationContextInternal(@Nullable Authentication auth,
83+
MethodInvocation mi) {
8384
return new MethodSecurityEvaluationContext(auth, mi, getParameterNameDiscoverer());
8485
}
8586

8687
@Override
87-
public EvaluationContext createEvaluationContext(Supplier<Authentication> authentication, MethodInvocation mi) {
88+
public EvaluationContext createEvaluationContext(Supplier<@Nullable Authentication> authentication,
89+
MethodInvocation mi) {
8890
MethodSecurityExpressionOperations root = createSecurityExpressionRoot(authentication, mi);
8991
MethodSecurityEvaluationContext ctx = new MethodSecurityEvaluationContext(root, mi,
9092
getParameterNameDiscoverer());
@@ -96,13 +98,13 @@ public EvaluationContext createEvaluationContext(Supplier<Authentication> authen
9698
* Creates the root object for expression evaluation.
9799
*/
98100
@Override
99-
protected MethodSecurityExpressionOperations createSecurityExpressionRoot(Authentication authentication,
101+
protected MethodSecurityExpressionOperations createSecurityExpressionRoot(@Nullable Authentication authentication,
100102
MethodInvocation invocation) {
101103
return createSecurityExpressionRoot(() -> authentication, invocation);
102104
}
103105

104-
private MethodSecurityExpressionOperations createSecurityExpressionRoot(Supplier<Authentication> authentication,
105-
MethodInvocation invocation) {
106+
private MethodSecurityExpressionOperations createSecurityExpressionRoot(
107+
Supplier<@Nullable Authentication> authentication, MethodInvocation invocation) {
106108
MethodSecurityExpressionRoot root = new MethodSecurityExpressionRoot(authentication);
107109
root.setThis(invocation.getThis());
108110
root.setPermissionEvaluator(getPermissionEvaluator());

core/src/main/java/org/springframework/security/access/expression/method/MethodSecurityExpressionRoot.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,11 +38,11 @@ class MethodSecurityExpressionRoot extends SecurityExpressionRoot implements Met
3838

3939
private @Nullable Object target;
4040

41-
MethodSecurityExpressionRoot(Authentication a) {
41+
MethodSecurityExpressionRoot(@Nullable Authentication a) {
4242
super(a);
4343
}
4444

45-
MethodSecurityExpressionRoot(Supplier<Authentication> authentication) {
45+
MethodSecurityExpressionRoot(Supplier<@Nullable Authentication> authentication) {
4646
super(authentication);
4747
}
4848

core/src/main/java/org/springframework/security/authorization/AuthenticatedAuthorizationManager.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@
1818

1919
import java.util.function.Supplier;
2020

21+
import org.jspecify.annotations.Nullable;
22+
2123
import org.springframework.security.authentication.AuthenticationTrustResolver;
2224
import org.springframework.security.authentication.AuthenticationTrustResolverImpl;
2325
import org.springframework.security.core.Authentication;
@@ -111,7 +113,7 @@ public static <T> AuthenticatedAuthorizationManager<T> anonymous() {
111113
* @return an {@link AuthorizationDecision}
112114
*/
113115
@Override
114-
public AuthorizationResult authorize(Supplier<Authentication> authentication, T object) {
116+
public AuthorizationResult authorize(Supplier<@Nullable Authentication> authentication, T object) {
115117
boolean granted = this.authorizationStrategy.isGranted(authentication.get());
116118
return new AuthorizationDecision(granted);
117119
}

core/src/main/java/org/springframework/security/authorization/AuthoritiesAuthorizationManager.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919
import java.util.Collection;
2020
import java.util.function.Supplier;
2121

22+
import org.jspecify.annotations.Nullable;
23+
2224
import org.springframework.security.access.hierarchicalroles.NullRoleHierarchy;
2325
import org.springframework.security.access.hierarchicalroles.RoleHierarchy;
2426
import org.springframework.security.core.Authentication;
@@ -55,7 +57,8 @@ public void setRoleHierarchy(RoleHierarchy roleHierarchy) {
5557
* @return an {@link AuthorityAuthorizationDecision}
5658
*/
5759
@Override
58-
public AuthorizationResult authorize(Supplier<Authentication> authentication, Collection<String> authorities) {
60+
public AuthorizationResult authorize(Supplier<@Nullable Authentication> authentication,
61+
Collection<String> authorities) {
5962
boolean granted = isGranted(authentication.get(), authorities);
6063
return new AuthorityAuthorizationDecision(granted, AuthorityUtils.createAuthorityList(authorities));
6164
}

core/src/main/java/org/springframework/security/authorization/AuthorityAuthorizationManager.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919
import java.util.Set;
2020
import java.util.function.Supplier;
2121

22+
import org.jspecify.annotations.Nullable;
23+
2224
import org.springframework.security.access.hierarchicalroles.NullRoleHierarchy;
2325
import org.springframework.security.access.hierarchicalroles.RoleHierarchy;
2426
import org.springframework.security.core.Authentication;
@@ -137,7 +139,7 @@ private static String[] toNamedRolesArray(String rolePrefix, String[] roles) {
137139
* {@inheritDoc}
138140
*/
139141
@Override
140-
public AuthorizationResult authorize(Supplier<Authentication> authentication, T object) {
142+
public AuthorizationResult authorize(Supplier<@Nullable Authentication> authentication, T object) {
141143
return this.delegate.authorize(authentication, this.authorities);
142144
}
143145

0 commit comments

Comments
 (0)