您觉得本文档还缺少什么内容?可以自己补充~
bc-util-serurity-starter 模块主要实现了2个功能, URI权限拦截 和 用户信息注入.
URI权限拦截器
- 原理
项目启动时, 会加载到spring.factories文件中的
SecurityConfiguration
配置类, 然后实例UriSecurityPreAuthAspect
和VerifyAuthFunction
,UriSecurityPreAuthAspect
定义了@Around
, 会对标记了@PreAuth
注解和com.becypress.basic.base.controller.*.*(..)
包下的方法进行切入, 被切入的方法会进行权限验证, 验证逻辑是: 从上下文中取出当前用户, 然后远程查询认证服务, 获取当前用户的所有权限, 跟@PreAuth注解上的编码进行比对是否拥有指定权限. - 当子类Controller想要覆盖父类Controller 方法上的标记的@PreAuth权限编码, 必须在子类的方法上标记 @PreAuth 注解覆盖父类.
@Override
@PutMapping
// 重写父类方法后,可以@PreAuth 重写父类权限
@PreAuth("hasAnyPermission('{}edit')")
public R<User> update(UserUpdateDTO userUpdateDTO) {
//...
}
权限调试流程: UriSecurityPreAuthAspect#preAuth -> VerifyAuthFunction -> UserServiceImpl#getSysUserById
通过全局配置可以控制权限判断
bc:
security:
enabled: true # true 全局启用URI权限验证 false 全局禁用URI权限 设置成false后,标记的@PreAuth注解将会失效
caseSensitive: false # true: 区分大小写 false: 忽略大小写
注解
@PreAuth(enabled = false)
标记在类上,就禁用单个类的URI权限控制, 标记在单个方法上就禁用单个方法的URI权限控制@PreAuth 的replace属性用于替换 value中的
{}
@PreAuth(replace = "authority:dictionary:", value = "hasAnyPermission('{}view')")
@PreAuth 的 value 中可以配置的方法为
VerifyAuthFunction
类中的所有public 方法, 包括:permit : 忽略权限判断, 视为有权限
- denyAll :忽略权限判断, 视为无权限
- hasAnyPermission : 是否拥有任意一个指定的权限
- hasNoPermission : 是否不含指定权限
- hasPermission : 是否拥有所有指定权限
- hasAnyRole : 是否拥有任意一个指定的角色
- hasRole : 是否拥有所有指定权限
- hasNoRole : 是否不含指定角色 上述方法可以按下面的方式使用 :
@PreAuth("permit()")
@PreAuth("denyAll()")
@PreAuth("hasPermission('authority:user:add', 'authority:user:edit')")
@PreAuth("hasRole('SUPER_ADMIN')")
用户信息注入
本项目有2种方式可以在后端服务获取当前用户的信息. 推荐使用 @LoginUser SysUser user
获取用户详细信息.
- 通过 @LoginUser 注解获取用户详细信息
@PostMapping(value = "/postJson")
public R postJson(@LoginUser SysUser user) {
log.info("user={}", user); //用户完整信息
return R.success(user);
}
- 通过 ContextUtil 静态方法获取基本信息
ContextUtil.getUserId(); // 当前用户id
ContextUtil.getAccount(); //当前用户登录账号
ContextUtil.getName(); // 当前用户姓名
其中, 想要在Controller方法参数中使用 @LoginUser , 必须参考以下步骤:
- 在启动类标记 @EnableLoginArgResolver
- 在Controller方法中加入参数:
@LoginUser SysUser user
- 配置文件中配置:
bc:
security:
type: FEIGN
- 必须启动Oauth服务
遇到问题流程: ContextArgumentResolver#resolveArgument -> UserServiceImpl#getSysUserById
如何临时或者永久禁用URI权限
- common.yml bc.security.enabled = false 全局禁用 (支持运行时修改)
- bc-xxx-server.yml bc.security.enabled = false 当前服务禁用(支持运行时修改)
- Controller类上的注解, 禁用当前Controller (不支持运行时修改)
- Controller 方法上的注解,禁用当前方法(不支持运行时修改)
- 本地开发时,注释UriSecurityPreAuthAspect类的handleAuth(point) 方法,(支持运行时修改,但需要配合IDEA热部署)