Skip to content

Commit 40b84d3

Browse files
committed
Merge branch '6.4.x'
2 parents 6159e08 + 6c5b6d1 commit 40b84d3

File tree

3 files changed

+59
-9
lines changed

3 files changed

+59
-9
lines changed

config/src/test/java/org/springframework/security/config/annotation/method/configuration/PrePostMethodSecurityConfigurationTests.java

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2024 the original author or authors.
2+
* Copyright 2002-2025 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -58,6 +58,7 @@
5858
import org.springframework.context.annotation.Import;
5959
import org.springframework.context.annotation.Role;
6060
import org.springframework.context.event.EventListener;
61+
import org.springframework.core.annotation.AnnotationAwareOrderComparator;
6162
import org.springframework.core.annotation.AnnotationConfigurationException;
6263
import org.springframework.security.access.AccessDeniedException;
6364
import org.springframework.security.access.PermissionEvaluator;
@@ -1118,6 +1119,21 @@ public void preAuthorizeWhenDenyAllThenPublishesParameterizedAuthorizationDenied
11181119
assertThat(this.spring.getContext().getBean(AuthorizationDeniedListener.class).invocations).isEqualTo(1);
11191120
}
11201121

1122+
// gh-16819
1123+
@Test
1124+
void autowireWhenDefaultsThenAdvisorAnnotationsAreSorted() {
1125+
this.spring.register(MethodSecurityServiceConfig.class).autowire();
1126+
AuthorizationAdvisorProxyFactory proxyFactory = this.spring.getContext()
1127+
.getBean(AuthorizationAdvisorProxyFactory.class);
1128+
AnnotationAwareOrderComparator comparator = AnnotationAwareOrderComparator.INSTANCE;
1129+
AuthorizationAdvisor previous = null;
1130+
for (AuthorizationAdvisor advisor : proxyFactory) {
1131+
boolean ordered = previous == null || comparator.compare(previous, advisor) < 0;
1132+
assertThat(ordered).isTrue();
1133+
previous = advisor;
1134+
}
1135+
}
1136+
11211137
private static Consumer<ConfigurableWebApplicationContext> disallowBeanOverriding() {
11221138
return (context) -> ((AnnotationConfigWebApplicationContext) context).setAllowBeanDefinitionOverriding(false);
11231139
}

core/src/main/java/org/springframework/security/authorization/method/AuthorizationAdvisorProxyFactory.java

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2024 the original author or authors.
2+
* Copyright 2002-2025 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -47,6 +47,7 @@
4747
import org.springframework.aop.Pointcut;
4848
import org.springframework.aop.framework.AopInfrastructureBean;
4949
import org.springframework.aop.framework.ProxyFactory;
50+
import org.springframework.beans.factory.SmartInitializingSingleton;
5051
import org.springframework.core.annotation.AnnotationAwareOrderComparator;
5152
import org.springframework.lang.NonNull;
5253
import org.springframework.security.authorization.AuthorizationProxyFactory;
@@ -79,8 +80,8 @@
7980
* @author Josh Cummings
8081
* @since 6.3
8182
*/
82-
public final class AuthorizationAdvisorProxyFactory
83-
implements AuthorizationProxyFactory, Iterable<AuthorizationAdvisor>, AopInfrastructureBean {
83+
public final class AuthorizationAdvisorProxyFactory implements AuthorizationProxyFactory,
84+
Iterable<AuthorizationAdvisor>, AopInfrastructureBean, SmartInitializingSingleton {
8485

8586
private static final boolean isReactivePresent = ClassUtils.isPresent("reactor.core.publisher.Mono", null);
8687

@@ -125,6 +126,7 @@ public static AuthorizationAdvisorProxyFactory withDefaults() {
125126
advisors.add(new PostFilterAuthorizationMethodInterceptor());
126127
AuthorizationAdvisorProxyFactory proxyFactory = new AuthorizationAdvisorProxyFactory(advisors);
127128
proxyFactory.addAdvisor(new AuthorizeReturnObjectMethodInterceptor(proxyFactory));
129+
AnnotationAwareOrderComparator.sort(proxyFactory.advisors);
128130
return proxyFactory;
129131
}
130132

@@ -142,9 +144,15 @@ public static AuthorizationAdvisorProxyFactory withReactiveDefaults() {
142144
advisors.add(new PostFilterAuthorizationReactiveMethodInterceptor());
143145
AuthorizationAdvisorProxyFactory proxyFactory = new AuthorizationAdvisorProxyFactory(advisors);
144146
proxyFactory.addAdvisor(new AuthorizeReturnObjectMethodInterceptor(proxyFactory));
147+
AnnotationAwareOrderComparator.sort(proxyFactory.advisors);
145148
return proxyFactory;
146149
}
147150

151+
@Override
152+
public void afterSingletonsInstantiated() {
153+
AnnotationAwareOrderComparator.sort(this.advisors);
154+
}
155+
148156
/**
149157
* Proxy an object to enforce authorization advice.
150158
*
@@ -165,7 +173,6 @@ public static AuthorizationAdvisorProxyFactory withReactiveDefaults() {
165173
*/
166174
@Override
167175
public Object proxy(Object target) {
168-
AnnotationAwareOrderComparator.sort(this.advisors);
169176
if (target == null) {
170177
return null;
171178
}
@@ -178,9 +185,9 @@ public Object proxy(Object target) {
178185
}
179186
ProxyFactory factory = new ProxyFactory(target);
180187
factory.addAdvisors(this.authorizationProxy);
181-
for (Advisor advisor : this.advisors) {
182-
factory.addAdvisors(advisor);
183-
}
188+
List<Advisor> advisors = new ArrayList<>(this.advisors);
189+
AnnotationAwareOrderComparator.sort(advisors);
190+
factory.addAdvisors(advisors);
184191
factory.addInterface(AuthorizationProxy.class);
185192
factory.setOpaque(true);
186193
factory.setProxyTargetClass(!Modifier.isFinal(target.getClass().getModifiers()));

core/src/test/java/org/springframework/security/authorization/AuthorizationAdvisorProxyFactoryTests.java

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2024 the original author or authors.
2+
* Copyright 2002-2025 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -40,6 +40,7 @@
4040
import org.junit.jupiter.api.Test;
4141

4242
import org.springframework.aop.Pointcut;
43+
import org.springframework.core.annotation.AnnotationAwareOrderComparator;
4344
import org.springframework.security.access.AccessDeniedException;
4445
import org.springframework.security.access.prepost.PreAuthorize;
4546
import org.springframework.security.authentication.TestAuthentication;
@@ -360,6 +361,32 @@ public void proxyWhenDefaultsThenInstanceOfAuthorizationProxy() {
360361
assertThat(target).isSameAs(this.flight);
361362
}
362363

364+
// gh-16819
365+
@Test
366+
void advisorsWhenWithDefaultsThenAreSorted() {
367+
AuthorizationAdvisorProxyFactory proxyFactory = AuthorizationAdvisorProxyFactory.withDefaults();
368+
AnnotationAwareOrderComparator comparator = AnnotationAwareOrderComparator.INSTANCE;
369+
AuthorizationAdvisor previous = null;
370+
for (AuthorizationAdvisor advisor : proxyFactory) {
371+
boolean ordered = previous == null || comparator.compare(previous, advisor) < 0;
372+
assertThat(ordered).isTrue();
373+
previous = advisor;
374+
}
375+
}
376+
377+
// gh-16819
378+
@Test
379+
void advisorsWhenWithReactiveDefaultsThenAreSorted() {
380+
AuthorizationAdvisorProxyFactory proxyFactory = AuthorizationAdvisorProxyFactory.withReactiveDefaults();
381+
AnnotationAwareOrderComparator comparator = AnnotationAwareOrderComparator.INSTANCE;
382+
AuthorizationAdvisor previous = null;
383+
for (AuthorizationAdvisor advisor : proxyFactory) {
384+
boolean ordered = previous == null || comparator.compare(previous, advisor) < 0;
385+
assertThat(ordered).isTrue();
386+
previous = advisor;
387+
}
388+
}
389+
363390
private Authentication authenticated(String user, String... authorities) {
364391
return TestAuthentication.authenticated(TestAuthentication.withUsername(user).authorities(authorities).build());
365392
}

0 commit comments

Comments
 (0)