IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 开发测试 -> SpringSecurity系列之授权与注解 -> 正文阅读

[开发测试]SpringSecurity系列之授权与注解

SpringSecurity系列之授权与注解

本文中所使用的技术栈如下:
SpringBoot 2.6.2
MyBatis Plus 3.5.0
SpringSecurity 5.6.1

本文中的代码将基于上文[SpringSecurity系列之基于数据库认证]

一、基于配置类的权限控制

1.修改SpringSecurity配置类

重写configure(HttpSecurity http) 方法,给用户访问的URL中的路径进行权限限制,限定只有该角色或者权限的用户才能够进行访问。

@Override
protected void configure(HttpSecurity http) throws Exception {
   http.formLogin();

   http.authorizeRequests()
         // 有该角色才能访问
         .antMatchers("/test-user").hasRole("user")
         .antMatchers("/test-admin").hasRole("admin")
         // 登录可访问
         .anyRequest().authenticated();


   //关闭csrf
   http.csrf().disable();
}

上述代码中所示,匹配/test-user的路径必须有user角色才能够访问,匹配 /test-admin 的路径必须有admin角色才能够访问,.anyRequest().authenticated(); 表示其他的任何请求只需登录即可访问。

2.修改UserDetailsService实现类进行用户授权

而用户的授权我们在UserDetailsService实现类中设置用户的权限/角色,代码如下:

@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
   // 通过username查询数据库中的用户信息
   QueryWrapper<SysUser> queryWrapper = new QueryWrapper<>();
   queryWrapper.eq("username", username);
   // 获取数据库查询的用户信息
   SysUser sysUser = this.userMapper.selectOne(queryWrapper);
   // 校验用户对象是否存在
   if (Objects.isNull(sysUser)) {
      throw new  UsernameNotFoundException("用户不存在");
   }
   User.UserBuilder builder = User.builder();
   UserDetails admin = builder.username(sysUser.getUsername())
         // 实际上是从数据库中直接取出加密后的密码,而不是在此处加密
         .password(new BCryptPasswordEncoder().encode(sysUser.getPassword()))
         .roles("admin")
         .build();
   // 返回用户对象
   return admin;
}

代码中构造UserDetails对象时调用的roles方法就是给该登录用户设置admin角色。

3.创建角色对应的接口

我们创建两个两个匹配路径的接口用于测试角色授权

@GetMapping("/test-user")
public String testUser() {
   return "SpringSecurity-user";
}

@GetMapping("/test-admin")
public String testAdmin() {
   return "SpringSecurity-admin";
}

4.测试标题权限访问

测试结果如下:
在这里插入图片描述
在这里插入图片描述

如上当我们访问/test-user接口时,报403异常,表示我们没有访问该接口的权限,因为我们只有admin角色,而没有设置user角色。

5.自定义403无权访问页面

在static目录下创建一个403.html文件,内容如下:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>403</title>

</head>
<body>
    <h1>很抱歉,您没有访问权限!</h1>
</body>
</html>

在SpringSecurity配置类中添加自定义403访问页面的路径

@Override
protected void configure(HttpSecurity http) throws Exception {
   http.formLogin();

   http.authorizeRequests()
         // 有该角色才能访问
         .antMatchers("/test-user").hasRole("user")
         .antMatchers("/test-admin").hasRole("admin")
         // 登录可访问
         .anyRequest().authenticated();

   // 设置403访问页面
   http.exceptionHandling().accessDeniedPage("/403.html");

   //关闭csrf
   http.csrf().disable();
}

如图中代码,接下来我们访问/test-user接口,结果如下:
在这里插入图片描述

二、基于注解的权限控制

基于注解的权限控制比较简单,我们只需要在接口方法上添加权限注解,并开启注解配置即可。

1.@Secured注解的使用

使用该注解做权限控制需要开启如下配置:

@Configuration
@EnableGlobalMethodSecurity(securedEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
	// ....
}

在SpringSecurity配置类中或者SpringBoot启动类上添加 @EnableGlobalMethodSecurity注解,并设置securedEnabled属性值为ture 表示开启@Secured注解的使用。

创建一个接口并添加@Secured注解控制接口的访问权限,代码如下:

@Secured({"ROLE_admin"})
@GetMapping("/test-user2")
public String testUser2() {
   return "SpringSecurity-user2";
}

@Secured注解中添加字符串数组,每一个字符串数组代码一个角色,角色必须以ROLE_开头。
而在UserDetailsService实现类中给用户对象添加角色为ROLE_以后的字符串,如下:

UserDetails admin = builder.username(sysUser.getUsername())
      // 实际上是从数据库中直接取出加密后的密码,而不是在此处加密
      .password(new BCryptPasswordEncoder().encode(sysUser.getPassword()))
      .roles("admin")
      .build();

访问结果如下:
在这里插入图片描述

2.@PreAuthorize注解的使用

使用该注解同样需要开启配置@EnableGlobalMethodSecurity注解,不过是需要设置prePostEnabled属性为true。
代码如下:

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
	// ...
}

创建一个接口并添加@PreAuthorize注解

@PreAuthorize("hasRole('ROLE_admin')")
@GetMapping("/test-user3")
public String testUser3() {
   return "SpringSecurity-user3";
}

在该注解中需要添加的是角色权限的表达式,以现在用户访问的权限。
上述接口中表示访问该接口必须有admin角色

在@PreAuthority注解中角色可以不用添加ROLE_前缀,系统将会自动帮我们添加前缀

@PreAuthorize("hasRole('admin')")
@GetMapping("/test-user5")
public String testUser5() {
   return "SpringSecurity-user5";
}

使用如上代码也可完成admin角色控制接口

其他表达式:

  • hasAnyRole: 可添加多个角色,而hasRole只可添加一个角色
  • hasAuthority: 添加一个访问权限,只能添加一个
  • hasAnyAuthority: 添加多个访问权限
UserDetails admin = builder.username(sysUser.getUsername())
      // 实际上是从数据库中直接取出加密后的密码,而不是在此处加密
      .password(new BCryptPasswordEncoder().encode(sysUser.getPassword()))
      // .roles("admin")
      .authorities("auth1")
      .build();

如上代码给用户添加访问权限,通过调用authorities方法,设置访问权限。

警告:roles()和authorities()只能生效一个,后调用的会覆盖之前调用的权限,如上将roles()注释掉,即使不注释掉改方法,也无法使其生效。

  • permitAll() : 表示只需登录即可访问,无需任何权限
  • denyAll(): 表示拒绝访问,任何权限均无法访问
  • isAnonymous(): 表示匿名用户可访问

3.@PostAuthorize注解的使用

使用方式与第二点相同,区别在于该注解的权限校验是进入方法之后,在返回结果之前进行校验。

注解中的SpEL表达式参考 SecurityExpressionRoot 类中的方法。

  开发测试 最新文章
pytest系列——allure之生成测试报告(Wind
某大厂软件测试岗一面笔试题+二面问答题面试
iperf 学习笔记
关于Python中使用selenium八大定位方法
【软件测试】为什么提升不了?8年测试总结再
软件测试复习
PHP笔记-Smarty模板引擎的使用
C++Test使用入门
【Java】单元测试
Net core 3.x 获取客户端地址
上一篇文章      下一篇文章      查看所有文章
加:2022-02-03 01:26:47  更:2022-02-03 01:27:01 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/18 2:24:09-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码