GlobalMethodSecurityConfiguration 在 Spring Boot 3 中已弃用,如何在 3 中创建自定义表达式处理程序?

Thi*_*mal 6 java spring-security spring-boot

createExpressionHandler目前,我已经通过覆盖GlobalMethodSecurityConfiguration. 代码是

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class MethodSecurityConfig extends GlobalMethodSecurityConfiguration {

    Logger logger = LoggerFactory.getLogger(this.getClass());
    
    @Autowired
    private ApplicationContext applicationContext;
    
    @Override
    protected MethodSecurityExpressionHandler createExpressionHandler() {
        CustomMethodSecurityExpressionHandler expressionHandler = new CustomMethodSecurityExpressionHandler();
        expressionHandler.setPermissionEvaluator(new CustomPermissionEvaluator());
        expressionHandler.setApplicationContext(applicationContext);
        return expressionHandler;
    }
    
}
Run Code Online (Sandbox Code Playgroud)

-- CustomMethodSecurityExpressionHandler 类

public class CustomMethodSecurityExpressionHandler extends DefaultMethodSecurityExpressionHandler {
    
    private ApplicationContext applicationContext;
    private AuthenticationTrustResolver trustResolver = new AuthenticationTrustResolverImpl();

    @Override
    protected MethodSecurityExpressionOperations createSecurityExpressionRoot(Authentication authentication,
            MethodInvocation invocation) {
        CustomMethodSecurityExpressionRoot root = new CustomMethodSecurityExpressionRoot(authentication);
        root.setPermissionEvaluator(getPermissionEvaluator());
        root.setTrustResolver(this.trustResolver);
        root.setRoleHierarchy(getRoleHierarchy());
        root.setG(this.applicationContext.getBean(CustomTraversalSource.class));
        return root;
    }
    
    //This setter method will be called from the config class
    @Override
    public void setApplicationContext(ApplicationContext applicationContext) {
        super.setApplicationContext(applicationContext);
        this.applicationContext=applicationContext;
    }
}
Run Code Online (Sandbox Code Playgroud)

和 CustomPermissionEvaluator

@Component
public class CustomPermissionEvaluator implements PermissionEvaluator {

    @Override
    public boolean hasPermission(Authentication authentication, Object targetDomainObject, Object permission) {
        if ((authentication == null) || (targetDomainObject == null) || !(permission instanceof String)){
            return false;
        }
        String targetType = targetDomainObject.getClass().getSimpleName().toUpperCase();
        
        return hasPrivilege(authentication, targetType, permission.toString().toUpperCase());
    }

    @Override
    public boolean hasPermission(Authentication authentication, Serializable targetId, String targetType,
            Object permission) {
        if ((authentication == null) || (targetType == null) || !(permission instanceof String)) {
            return false;
        }
        return hasPrivilege(authentication, targetType.toUpperCase(), 
          permission.toString().toUpperCase());
    }

    private boolean hasPrivilege(Authentication authentication, String targetType, String permission) {
        for (GrantedAuthority grantedAuth : authentication.getAuthorities()) {
            if (grantedAuth.getAuthority().startsWith(targetType) && 
              grantedAuth.getAuthority().contains(permission)) {
                return true;
            }
        }
        return false;
    }

}
Run Code Online (Sandbox Code Playgroud)

Ale*_*nko 10

表达式处理程序

\n

为了自定义表达式处理机制,Spring Security 6.0 的参考文档建议通过在配置类中MethodSecurityExpressionHandler定义带注释的方法在 Context 中注册为 Bean 。@Bean建议使用修饰符标记该方法static,以便执行该方法,并在实例化和初始化配置类之前在 Context 中注册自定义表达式处理程序。

\n
\n

如果您需要自定义处理表达式的方式,\n您可以公开一个自定义MethodSecurityExpressionHandler,如下所示:

\n
@Bean\nstatic MethodSecurityExpressionHandler\nmethodSecurityExpressionHandler() {\n    // instantiating the handler\n    return handler;\n}\n
Run Code Online (Sandbox Code Playgroud)\n

我们使用方法公开 MethodSecurityExpressionHandler,static以确保 Spring 在初始化 SpringSecurityxe2x80x99s 方法安全@Configuration类之前发布它。

\n
\n

@EnableMethodSecurity

\n

@EnableMethodSecurity注释是已弃用的推荐替代品@EnableGlobalMethodSecurity

\n

它的属性prePostEnabled默认设置为true

\n

因此,要启用@PreAuthorize/@PostAuthorize@PreFilter/@PostFilterwhich是最广泛使用的注释来自定义方法级别的访问控制,您可以@EnableMethodSecurity在不提供任何参数的情况下应用。

\n