SpringSecurity如何使用注解控制权限

2022年8月9日10:17:54

一般的系统在权限设计上,都会分为角色、权限(RDBC),复杂一点的可能会有用户组、组织之类的概念。

用户的权限是写死的,对应于后台的接口或者资源,是没办法改变的,一般不对用户开放修改权限。

管理员用户可以通过给角色分配权限的方式,来实现访问控制。

所以当我们写过滤器,或者用一些安全框架时(比如Shiro,Spring Security),也需要将可变的“角色”,转化为不可变的“权限”,注入到框架中。

具体的可以看我之前写的一篇(Spring Security整合jwt完整版):https://blog.csdn.net/qq_37855749/article/details/111300906

注入当前用户的权限后,就需要进行访问控制了。

常见的做法有

1、路径比对

之前有个项目用过一次,定义一个过滤器,添加到security的过滤链中,在这个过滤器中做这么一件事:

分析当前访问路径所需要的权限,检查当前用户是否具有该权限,做一个对比,根据对比结果来决定当前用户是否可以访问该资源。

这种做法的好处是代码的入侵性不高,不需要再每个接口上加注解。但相对来说,显得不那么直观,可读性比较差,所以这次换个方法。

2、使用注解的方式

SpringSecurity使用注解来控制访问时,需要提前开启这个功能。

在配置类上加上注解

@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {

在接口中如此使用

    /**
     * 条件查询
     */
    @PreAuthorize("hasAuthority('IMPORT:SELECT')")
    @ApiOperation(value = "查询")
    @GetMapping("/list")
    public R<Page<Task>> list(TaskDto taskDto){
        //测试阶段,随机生成任务
        Random random = new Random();

        //todo
        int i = random.nextInt(4);
        if(i == 2) {
            metroServerAdapterService.reloadShelveTask();
        }
        Page<Task> list = taskService.list(taskDto);
        return R.ok(list);
    }

hasAuthority可以替换成hasRole,虽然可以达到相同的目的,但是在使用的方法上还是有些不同的。

hasRole要求内容必须以"ROLE_"开头,也是官方推荐的命名方式,否则没有效果。但是hasAuthority没有限制,数据库中怎样写的,代码里就怎么写。

同样的功能的注解为什么要有两个名字呢。或许这么做可能在语义上比较清晰明确一点,将角色与权限这两个概念稍加区分。

仔细想一下,确实有些小型的系统或许压根就不需要权限,只有给用户分配角色,没有给角色分配权限这一过程。这样的话,角色也是不可变的,就可以根据角色来做访问控制了。

但考虑通用性,个人觉得用hasAuthority就可以了。

  • 作者:小楼夜听雨QAQ
  • 原文链接:https://blog.csdn.net/qq_37855749/article/details/113355890
    更新时间:2022年8月9日10:17:54 ,共 1317 字。