Spring Security实现基于RBAC的权限表达式动态访问控制的操作方法

下面是Spring Security实现基于RBAC的权限表达式动态访问控制的操作方法的完整攻略:

步骤一:初始化Spring Security

使用Spring Security提供的依赖,在pom.xml文件中配置以下依赖项:

<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-web</artifactId>
    <version>5.2.2.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-config</artifactId>
    <version>5.2.2.RELEASE</version>
</dependency>

完成后,需要在Spring应用程序的配置文件中启用Spring Security:

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
     @Override
     protected void configure(HttpSecurity http) throws Exception {
         http.authorizeRequests()
             .antMatchers("/admin/**").hasRole("ADMIN")
             .antMatchers("/user/**").hasRole("USER")
             .and()
             .formLogin();
     }

     @Override
     public void configure(WebSecurity web) throws Exception {
         web.ignoring()
             .antMatchers("/resources/**");
     }

     @Override
     public void configure(AuthenticationManagerBuilder auth) throws Exception {
         auth.inMemoryAuthentication()
             .withUser("admin").password("{noop}admin").roles("ADMIN")
             .and()
             .withUser("user").password("{noop}user").roles("USER");
     }
}

步骤二:配置基于RBAC的权限表达式

在Spring Security中使基于RBAC的权限表达式成为真正动态的,可以使用Spring EL,这样就可以对当前用户的角色进行动态处理。

首先,需要定义一个角色和对应的权限,可以将这些数据存储到数据库中:

CREATE TABLE Role (
  id INTEGER NOT NULL AUTO_INCREMENT PRIMARY KEY,
  name TEXT NOT NULL,
  description TEXT DEFAULT NULL
);

CREATE TABLE Permission (
  id INTEGER NOT NULL AUTO_INCREMENT PRIMARY KEY,
  name TEXT NOT NULL,
  description TEXT DEFAULT NULL
);

CREATE TABLE Role_Permission (
  role_id INTEGER NOT NULL,
  permission_id INTEGER NOT NULL,
  PRIMARY KEY (role_id, permission_id),
  CONSTRAINT ROLE_PERM_ROLE_FK FOREIGN KEY (role_id)
    REFERENCES Role (id),
  CONSTRAINT ROLE_PERM_PERM_FK FOREIGN KEY (permission_id)
    REFERENCES Permission (id)
);

INSERT INTO Role (name, description) VALUES ('admin', '管理者');
INSERT INTO Role (name, description) VALUES ('user', '普通用户');

INSERT INTO Permission (name, description) VALUES ('create', '创建');
INSERT INTO Permission (name, description) VALUES ('read', '读取');
INSERT INTO Permission (name, description) VALUES ('update', '更新');
INSERT INTO Permission (name, description) VALUES ('delete', '删除');

INSERT INTO Role_Permission (role_id, permission_id) VALUES (1, 1);
INSERT INTO Role_Permission (role_id, permission_id) VALUES (1, 2);
INSERT INTO Role_Permission (role_id, permission_id) VALUES (1, 3);
INSERT INTO Role_Permission (role_id, permission_id) VALUES (1, 4);
INSERT INTO Role_Permission (role_id, permission_id) VALUES (2, 2);

接下来,需要在Spring Security的配置文件中添加以下代码来读取数据库中的角色和权限信息:

@EnableGlobalMethodSecurity(prePostEnabled = true)
public class AppConfig extends WebSecurityConfigurerAdapter {
    @Autowired
    private DataSource dataSource;

    @Bean
    public RoleHierarchyImpl roleHierarchy() {
        RoleHierarchyImpl roleHierarchy = new RoleHierarchyImpl();
        roleHierarchy.setHierarchy("ROLE_admin > ROLE_user");
        return roleHierarchy;
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests().antMatchers("/*").access("hasRole('admin') or hasRole('user')")
            .antMatchers("/admin/**").access("hasRole('admin')").and().formLogin();
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        JdbcUserDetailsManager userDetailsService = new JdbcUserDetailsManager();
        userDetailsService.setDataSource(dataSource);
        userDetailsService.setSqlUsersByUsernameQuery(
                "select username,password,enabled from users where username=?");
        userDetailsService.setSqlRolesByUsernameQuery(
                "select u.username, r.name from users u, user_roles ur, role r where u.id = ur.user_id and ur.role_id = r.id and u.username=?");
        auth.userDetailsService(userDetailsService);
    }
}

步骤三:添加角色和权限

在定义了角色和权限之后,需要为用户分配角色和权限:

ALTER TABLE users
ADD COLUMN enabled BOOLEAN DEFAULT TRUE NOT NULL;

CREATE TABLE user_roles (
  user_id INTEGER NOT NULL,
  role_id INTEGER NOT NULL,
  PRIMARY KEY (user_id, role_id),
  CONSTRAINT users_roles_users_FK FOREIGN KEY (user_id)
    REFERENCES users (id),
  CONSTRAINT users_roles_roles_FK FOREIGN KEY (role_id)
    REFERENCES Role (id)
);

INSERT INTO users VALUES (DEFAULT, 'admin', 'admin@example.com', 'password', TRUE);
INSERT INTO users VALUES (DEFAULT, 'user', 'user@example.com', 'password', TRUE);

INSERT INTO user_roles VALUES (1, 1);
INSERT INTO user_roles VALUES (2, 2);

示例一:使用Spring EL动态控制页面访问权限

首先,创建一个基本的Spring MVC控制器:

@Controller
public class HomeController {

    @GetMapping("/")
    @PreAuthorize("hasRole('USER')")
    public String index(Model model) {
        return "index";
    }

    @GetMapping("/admin")
    @PreAuthorize("hasRole('ADMIN')")
    public String admin(Model model) {
        return "admin";
    }
}

在访问/index时,只有拥有USER角色的用户可以查看,而在访问/admin时,只有拥有ADMIN角色的用户才能查看。

示例二:使用代码动态控制页面访问权限

在使用代码动态控制页面访问权限时,可以在Spring Security的配置文件中添加以下代码:

@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class SecurityConfig extends WebSecurityConfigurerAdapter {
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
            .antMatchers("/user/**").access("hasRole('USER') or hasRole('ADMIN')")
            .antMatchers("/admin/**").access("hasRole('ADMIN')")
        .and()
            .formLogin();
    }
}

在访问/user/时,只有拥有USER或者ADMIN角色的用户可以查看,而在访问/admin/时,只有拥有ADMIN角色的用户才能查看。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Spring Security实现基于RBAC的权限表达式动态访问控制的操作方法 - Python技术站

(0)
上一篇 2023年5月20日
下一篇 2023年5月20日

相关文章

  • Springboot+mybatis plus找不到mapper.xml的问题解决

    问题描述: 使用Springboot和mybatis plus开发过程中,出现了找不到mapper.xml的错误,导致无法正常进行数据库操作。 问题原因: 在Springboot中使用mybatis plus进行数据访问时,需要将.xml文件放在classpath根目录下或者mapper接口所在的包下。而有时候我们的项目结构并不是标准的Maven或Gradl…

    Java 2023年5月26日
    00
  • Hibernate识别数据库特有字段实例详解

    让我为您详细讲解“Hibernate识别数据库特有字段实例详解”的完整攻略。 在使用Hibernate进行开发时,有些时候我们需要识别一些数据库特有的字段,如MySQL中的ENUM类型、PostgreSQL中的ARRAY类型等。这些字段并不在Hibernate的基础数据类型中,所以我们需要进行额外配置。 下面是如何识别MySQL中的ENUM类型的示例: 首先…

    Java 2023年5月20日
    00
  • 堆内存和栈内存的区别是什么?

    以下是关于堆内存和栈内存的区别的完整使用攻略: 堆内存和栈内存的区别是什么? 堆内存和栈内存都是计算机内存中的一部分,但它们的使用方式和特点不同。 堆内存是指由程序员手动分配和释放的内存空间,通常用于存储动态分配的数据结构,如数组和对象等。堆内存的大小通常比栈内存大,但是它的分配和释放速度较慢。 栈内存是指由编译器自动分配和释放的内存空间,通常用于存储局部变…

    Java 2023年5月12日
    00
  • Spring Security表单配置过程分步讲解

    下面我将详细讲解 Spring Security 表单配置过程分步讲解的攻略。 一、添加 Spring Security 依赖 首先需要在项目中添加 Spring Security 的依赖,可以在 Maven 的 pom.xml 文件中添加以下内容,或者在 Gradle 配置文件中添加相应的依赖。 <dependency> <groupId…

    Java 2023年6月3日
    00
  • 微信小程序获取手机号的完整实例(Java后台实现)

    下面我来详细讲解“微信小程序获取手机号的完整实例(Java后台实现)”的攻略。 1. 前言 在微信小程序开发中,获取用户手机号是必不可少的一个功能,下面将会介绍如何实现微信小程序获取手机号的完整攻略,并且以两个示例说明。 2. 获取用户手机号的流程 获取用户手机号的流程分为三个步骤: 微信小程序前端获取用户手机号码加密信息(encryptedData)和加密…

    Java 2023年5月23日
    00
  • Spring Boot统一处理全局异常的实战教程

    1. 简介 Spring Boot统一处理全局异常是开发中必须掌握的技能,本文将介绍Spring Boot如何统一处理全局异常。这种异常处理方式可以使我们更好地监控和维护自己的应用程序。 2. 异常处理方式 在Spring Boot中,可以通过@ControllerAdvice注解来处理全局异常。 @ControllerAdvice public class…

    Java 2023年5月27日
    00
  • JavaWeb Servlet实现文件上传与下载功能实例

    下面是 “JavaWeb Servlet实现文件上传与下载功能实例” 的完整攻略。 一、准备工作 在开始实现文件上传与下载功能之前,我们需要准备如下环境和工具: JDK:Java开发环境,最好使用JDK 1.8及以上版本; Eclipse:Java IDE,也可以使用其他Java IDE,比如IntelliJ IDEA等; Tomcat:JavaWeb服务器…

    Java 2023年5月19日
    00
  • 详解hibernate自动创建表的配置

    下面是详解Hibernate自动创建表的配置的完整攻略。 概述 Hibernate是一种流行的面向对象关系映射(ORM)框架,可用于将Java对象与关系型数据库(如MySQL)之间进行映射。Hibernate不仅提供了用于执行CRUD(创建、读取、更新和删除)操作的API,还可以自动创建与Java实体类对应的数据库表。在本攻略中,我们将重点探讨Hiberna…

    Java 2023年5月20日
    00
合作推广
合作推广
分享本页
返回顶部