@@ -25,6 +25,9 @@ import org.springframework.beans.factory.config.BeanPostProcessor
25
25
import org.springframework.context.ApplicationListener
26
26
import org.springframework.context.annotation.Bean
27
27
import org.springframework.security.access.AccessDecisionManager ;
28
+ import org.springframework.security.access.PermissionEvaluator
29
+ import org.springframework.security.access.hierarchicalroles.RoleHierarchy
30
+ import org.springframework.security.access.hierarchicalroles.RoleHierarchyImpl
28
31
import org.springframework.security.access.event.AuthorizedEvent
29
32
import org.springframework.security.access.vote.AffirmativeBased
30
33
import org.springframework.security.authentication.RememberMeAuthenticationToken
@@ -35,6 +38,7 @@ import org.springframework.security.config.annotation.web.builders.HttpSecurity
35
38
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity
36
39
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter
37
40
import org.springframework.security.config.annotation.web.configurers.ExpressionUrlAuthorizationConfigurerConfigs.CustomExpressionRootConfig
41
+ import org.springframework.security.core.Authentication
38
42
import org.springframework.security.core.authority.AuthorityUtils
39
43
import org.springframework.security.web.access.intercept.FilterSecurityInterceptor
40
44
@@ -574,4 +578,119 @@ public class ExpressionUrlAuthorizationConfigurerTests extends BaseSpringSpec {
574
578
}
575
579
576
580
}
581
+
582
+ def " permissionEvaluator autowired" () {
583
+ setup :
584
+ loadConfig(PermissionEvaluatorConfig )
585
+ when : " invoke hasPermission expression that allows access"
586
+ super . setup()
587
+ login()
588
+ request. servletPath = " /allow/1"
589
+ springSecurityFilterChain. doFilter(request, response, chain)
590
+ then : " permissionEvaluator with id and type works - allows access"
591
+ response. status == HttpServletResponse . SC_OK
592
+ when : " invoke hasPermission expression that denies access"
593
+ super . setup()
594
+ login()
595
+ request. servletPath = " /deny/1"
596
+ springSecurityFilterChain. doFilter(request, response, chain)
597
+ then : " permissionEvaluator with id and type works - denies access"
598
+ response. status == HttpServletResponse . SC_FORBIDDEN
599
+ when : " invoke hasPermission expression that allows access"
600
+ super . setup()
601
+ login()
602
+ request. servletPath = " /allowObject/1"
603
+ springSecurityFilterChain. doFilter(request, response, chain)
604
+ then : " permissionEvaluator with object works - allows access"
605
+ response. status == HttpServletResponse . SC_OK
606
+ when : " invoke hasPermission expression that denies access"
607
+ super . setup()
608
+ login()
609
+ request. servletPath = " /denyObject/1"
610
+ springSecurityFilterChain. doFilter(request, response, chain)
611
+ then : " permissionEvaluator with object works - denies access"
612
+ response. status == HttpServletResponse . SC_FORBIDDEN
613
+ }
614
+
615
+ @EnableWebSecurity
616
+ static class PermissionEvaluatorConfig extends WebSecurityConfigurerAdapter {
617
+ @Override
618
+ protected void configure (HttpSecurity http ) throws Exception {
619
+ http
620
+ .authorizeRequests()
621
+ .antMatchers(" /allow/**" ). access(" hasPermission('ID', 'TYPE', 'PERMISSION')" )
622
+ .antMatchers(" /allowObject/**" ). access(" hasPermission('TESTOBJ', 'PERMISSION')" )
623
+ .antMatchers(" /deny/**" ). access(" hasPermission('ID', 'TYPE', 'NO PERMISSION')" )
624
+ .antMatchers(" /denyObject/**" ). access(" hasPermission('TESTOBJ', 'NO PERMISSION')" )
625
+ .anyRequest(). permitAll();
626
+ }
627
+
628
+ @Override
629
+ protected void configure (AuthenticationManagerBuilder auth ) throws Exception {
630
+ auth
631
+ .inMemoryAuthentication()
632
+ .withUser(" user" ). password(" password" ). roles(" USER" )
633
+ }
634
+
635
+ @Bean
636
+ public PermissionEvaluator permissionEvaluator (){
637
+ return new PermissionEvaluator (){
638
+ @Override
639
+ public boolean hasPermission (Authentication authentication , Object targetDomainObject , Object permission ) {
640
+ return " TESTOBJ" . equals(targetDomainObject) && " PERMISSION" . equals(permission);
641
+ }
642
+ @Override
643
+ public boolean hasPermission (Authentication authentication , Serializable targetId , String targetType ,
644
+ Object permission ) {
645
+ return " ID" . equals(targetId) && " TYPE" . equals(targetType) && " PERMISSION" . equals(permission);
646
+ }
647
+ };
648
+ }
649
+
650
+ }
651
+
652
+ @EnableWebSecurity
653
+ static class RoleHierarchyConfig extends WebSecurityConfigurerAdapter {
654
+ @Override
655
+ protected void configure (HttpSecurity http ) throws Exception {
656
+ http
657
+ .authorizeRequests()
658
+ .antMatchers(" /allow/**" ). access(" hasRole('XXX')" )
659
+ .antMatchers(" /deny/**" ). access(" hasRole('NOPE')" )
660
+ .anyRequest(). permitAll();
661
+ }
662
+
663
+ @Override
664
+ protected void configure (AuthenticationManagerBuilder auth ) throws Exception {
665
+ auth
666
+ .inMemoryAuthentication()
667
+ .withUser(" user" ). password(" password" ). roles(" USER" )
668
+ }
669
+
670
+ @Bean
671
+ public RoleHierarchy roleHierarchy (){
672
+ return new RoleHierarchyImpl (" USER > XXX" );
673
+ }
674
+
675
+ }
676
+
677
+ def " roleHierarchy autowired" () {
678
+ setup :
679
+ loadConfig(PermissionEvaluatorConfig )
680
+ when : " invoke roleHierarchy expression that allows access"
681
+ super . setup()
682
+ login()
683
+ request. servletPath = " /allow/1"
684
+ springSecurityFilterChain. doFilter(request, response, chain)
685
+ then : " permissionEvaluator with id and type works - allows access"
686
+ response. status == HttpServletResponse . SC_OK
687
+ when : " invoke roleHierarchy expression that denies access"
688
+ super . setup()
689
+ login()
690
+ request. servletPath = " /deny/1"
691
+ springSecurityFilterChain. doFilter(request, response, chain)
692
+ then : " permissionEvaluator with id and type works - denies access"
693
+ response. status == HttpServletResponse . SC_FORBIDDEN
694
+ }
695
+
577
696
}
0 commit comments