登陆认证权限控制(2)—— 基于Spring security 安全框架的权限管理 注解式权限控制 RABC模型

本文主要是介绍登陆认证权限控制(2)—— 基于Spring security 安全框架的权限管理 注解式权限控制 RABC模型,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

在这里插入图片描述

前言

登陆认证,权限控制是一个系统必不可少的部分,一个开放访问的系统能否在上线后稳定持续运行其实很大程度上取决于登陆认证和权限控制措施是否到位,不然可能系统刚刚上线就会夭折。

Spring Security 是一个能够为基于 Spring 的企业应用系统提供声明式的安全访问控制解决方案的安全框架。

本篇博客介绍Spring Security的使用,结合MySQL,Redis实现基于JWT的注解式的权限认证,并且可以实现给不同的用户显示不同的前端页面。

代码仓库:https://gitee.com/pet365/spring-security-demo

在这里插入图片描述

其他相关的权限文章如下:

  • 从http请求 到 cookie 到 session & 用 session控制 删改数据的权限

  • 使用token的权限验证方法 & 用户+角色+权限表设计 & SpringBoot项目应用

  • 登陆认证&权限控制(1)——从session到token认证的变迁 & session的问题分析 + CSRF攻击的认识

文章目录

  • 前言
  • 引出
  • 初识spring security安全框架
    • 快速入门
  • spring security的项目应用
    • 安全框架的配置
    • UserDetailsService接口
      • 1、基本概念
      • 2、UserDetailsService获取用户名,密码,权限
      • 3、UserInfo extends User
    • 设置拦截器handler
      • 1、登录成功的拦截器
      • 2、请求访问通过OncePerRequestFilter过滤器
  • 权限相关表设计
    • RBAC基于角色的访问控制
    • 数据库表设计
    • 查询语句
    • 权限的注解式控制
      • 配置打开注解
      • 使用注解控制权限
    • 给不同的用户显示不同的页面
      • 数据库表设计
      • 查询语句
      • 不同用户显示的效果
  • 总结
    • 附录:
      • 1、前端页面
      • 2、MySQL数据库语句

引出


1.Spring Security的使用,结合MySQL,Redis实现基于JWT的注解式的权限认证,并且可以实现给不同的用户显示不同的前端页面;
2.项目中的快速应用和使用,拦截器的设置,安全框架的配置;
3.权限表的设计,基于角色的访问控制RABC模型;
4.启动注解的配置,通过注解实现权限的控制;
5.给不同的用户显示不同的页面,相关的SQL以及前端页面;

初识spring security安全框架

Spring Security 是一个能够为基于 Spring 的企业应用系统提供声明式的安全访问控制解决方案的安全框架。它提供了一组可以在 Spring 应用上下文中配置的 Bean,充分利用了 Spring IoC(Inversion of Control 控制反转),DI(Dependency Injection 依赖注入)和 AOP(面向切面编程)功能,为应用系统提供声明式的安全访问控制功能,减少了为企业系统安全控制编写大量重复代码的工作。

Spring Security 拥有以下特性:

  • 对身份验证和授权的全面且可扩展的支持
  • 防御会话固定、点击劫持,跨站请求伪造等攻击
  • 支持 Servlet API 集成
  • 支持与 Spring Web MVC 集成

Spring、Spring Boot 和 Spring Security 三者的关系如下图所示:

在这里插入图片描述

快速入门

1、引入依赖

<!--springboot整合security坐标-->
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-security</artifactId>
</dependency>

2、创建一个控制器

@RestController
public class HelloController {@GetMapping("hello")public String hello(){return "Hello Spring security";}
}

3、启动项目

访问:http://localhost:8080/hello 结果打开的是一个登录页面,其实这时候我们的请求已经被保护起来了,要想访问,需要先登录。

在这里插入图片描述

Spring Security 默认提供了一个用户名为 user 的用户,其密码在控制台可以找到

spring security的项目应用

安全框架的配置

在这里插入图片描述

Spring Security 内置的 Password Encoder 有:

加密算法名称PasswordEncoder
NOOPNoOpPasswordEncoder.getInstance()
SHA256new StandardPasswordEncoder()
BCRYPT(官方推荐)new BCryptPasswordEncoder()
LDAPnew LdapShaPasswordEncoder()
PBKDF2new Pbkdf2PasswordEncoder()
SCRYPTnew SCryptPasswordEncoder()
MD4new Md4PasswordEncoder()
MD5new MessageDigestPasswordEncoder(“MD5”)
SHA_1new MessageDigestPasswordEncoder(“SHA-1”)
SHA_256new MessageDigestPasswordEncoder(“SHA-256”)

上述 Password Encoder 中有一个『无意义』的加密器:NoOpPasswordEncoder 。它对原始密码没有做任何处理(现在也被标记为废弃)。

记得使用 @SuppressWarnings(“deprecation”) 去掉 IDE 的警告信息。

package com.tianju.config;import com.tianju.config.security.handler.*;
import com.tianju.config.security.service.MyUserDetail;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;import javax.annotation.Resource;/*** 框架中自定义用户名和密码*/@EnableWebSecurity
@EnableGlobalMethodSecurity(securedEnabled = true,jsr250Enabled = true,prePostEnabled = true) // 开启注解式权限控制
public class SecurityConfig extends WebSecurityConfigurerAdapter {@Resourceprivate MyUserDetail myUserDetail;@Autowiredprivate LoginSuccessHandler loginSuccessHandler;@Autowiredprivate JwtHandler jwtHandler;@Value("${security.isOpen}")private Boolean isOpen;@Overridepublic void configure(AuthenticationManagerBuilder auth) throws Exception {/*** security硬性要求密码必须是密文*/PasswordEncoder passwordEncoder = new BCryptPasswordEncoder();// 对明文加密
//        String encode = passwordEncoder.encode("123");
//        System.out.println("加密后为:"+encode);
//        auth.inMemoryAuthentication().withUser("pet").password(encode).roles("admin");auth.userDetailsService(myUserDetail);}/*** 自定义表单,前端的页面* @param http* @throws Exception*/@Overrideprotected void configure(HttpSecurity http) throws Exception{if (isOpen){hasSecurity(http);}else {noSecurity(http);}}/*** 不加安全框架,放行所有请求* @param http*/private void noSecurity(HttpSecurity http) throws Exception {http.authorizeRequests().anyRequest().permitAll().and().csrf().disable();}private void hasSecurity(HttpSecurity http) throws Exception {// 自定义页面http.formLogin()  // 需要自定义表单.loginPage("/login.html") // 自己登陆页面.loginProcessingUrl("/api/user/login") // 登陆请求地址.successHandler(loginSuccessHandler) // 给前端返回json字符串.failureHandler(new LoginFailHandler()) // 登陆失败给前端的字符串Json.permitAll() // 对上面两个进行放行;http.exceptionHandling().accessDeniedHandler(new NoAuthorityHandler()) // 登陆后没有权限的返回字符串Json.authenticationEntryPoint(new NotLoginHandler()) // 未登录;//给接口配置权限//1:注解的方式//2:编码的方式http.authorizeRequests()// 无需登陆.antMatchers("/find","/api/img/upload","/api/img/hi","/api/map/fastMatch","/api/myLogin/username","/api/ali/pay","/api/ali/notify").permitAll() // 无需登陆.anyRequest().authenticated(); // 所有请求都拦截// 指定目标过滤器,填自己的过滤器http.addFilterBefore(jwtHandler, UsernamePasswordAuthenticationFilter.class);// 前后端项目中装禁用掉session(改用jwt)http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);// CSRF是指跨站请求伪造(Cross-site request forgery)// https://www.jianshu.com/p/5ac8deb775b0http.csrf().disable(); // 关闭csrf过滤器}/*** 加密的类必须放入IOC容器中* @return*/@Beanpublic PasswordEncoder passwordEncoder(){return new BCryptPasswordEncoder();}
}

UserDetailsService接口

1、基本概念

  • AuthenticationManager

    它是 “表面上” 的做认证和鉴权比对工作的那个人,它是认证和鉴权比对工作的起点。

    ProvierderManager 是 AuthenticationManager 接口的具体实现。

在这里插入图片描述

在这里插入图片描述

  • AuthenticationProvider

    它是 “实际上” 的做认证和鉴权比对工作的那个人。从命名上很容易看出,Provider 受 ProviderManager 的管理,ProviderManager 调用 Provider 进行认证和鉴权的比对工作。

    我们最常用到 DaoAuthenticationProvider 是 AuthenticationProvider 接口的具体实现。

在这里插入图片描述

  • UserDetailsService

    虽然 AuthenticationProvider 负责进行用户名和密码的比对工作,但是它并不清楚用户名和密码的『标准答案』,而标准答案则是由 UserDetailsService 来提供。简单来说,UserDetailsService 负责提供标准答案 ,以供 AuthenticationProvider 使用。

在这里插入图片描述

  • UserDetails

    UserDetails 它是存放用户认证信息和权限信息的标准答案的 “容器” ,它也是 UserDetailService “应该” 返回的内容。

在这里插入图片描述

  • PasswordEncoder

    Spring Security 要求密码不能是明文,必须经过加密器加密。这样,AuthenticationProvider 在做比对时,就必须知道『当初』密码时使用哪种加密器加密的。所以,AuthenticationProvider 除了要向 UserDetailsService 『要』用户名密码的标准答案之外,它还需要知道配套的加密算法(加密器)是什么

在这里插入图片描述

2、UserDetailsService获取用户名,密码,权限

在这里插入图片描述

3、UserInfo extends User

在这里插入图片描述

package com.tianju.config.security.entity;import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.User;import java.util.Collection;public class UserInfo extends User {private Integer userId; // 用户的idprivate String realName; // 真实姓名public UserInfo(String username, String password,Collection<? extends GrantedAuthority> authorities, Integer userId, String realName) {super(username, password, authorities);this.userId = userId;this.realName = realName;}public Integer getUserId() {return userId;}public String getRealName() {return realName;}
}

设置拦截器handler

在这里插入图片描述

1、登录成功的拦截器

在这里插入图片描述

2、请求访问通过OncePerRequestFilter过滤器

  • 1:是否携带了jwt

  • 2:解密清求头jwt

    不能解开:放行(到下一个过滤器》

    能解开:走到下一步

  • 3:对比redis中的jwt

    不一样:放行(到下一个过滤器)

    一样:走到下一步

  • 4:给jwt续期

  • 5:让容器中放入一个凭证(登陆凭证)

package com.tianju.config.security.handler;import com.tianju.config.security.service.MyUserDetail;
import com.tianju.util.JwtUtil;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.stereotype.Component;
import org.springframework.web.filter.OncePerRequestFilter;import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.Map;
import java.util.concurrent.TimeUnit;/*** 1:是否携带了jwt* 2:解密清求头jwt*      不能解开:放行(到下一个过滤器》*      能解开:走到下一步* 3:对比redis中的jwt*      不一样:放行(到下一个过滤器)*      一样:走到下一步* 4:给jwt续期* 5:让容器中放入一个凭证(登陆凭证)*/
@Component
@Slf4j
public class JwtHandler extends OncePerRequestFilter {@Autowiredprivate RedisTemplate<String,Object> stringRedisTemplate;@Autowiredprivate MyUserDetail myUserDetail;@SneakyThrows@Overrideprotected void doFilterInternal(HttpServletRequest request,HttpServletResponse response,FilterChain filterChain)throws ServletException, IOException {//1.获取请求头中的前端jwtString jwt = request.getHeader("jwt");//2.判断能否获取到jwtif (jwt == null) {filterChain.doFilter(request, response);log.warn("未携带Jwt");return;}//3.判断能否解密jwtif (!JwtUtil.decode(jwt)) {filterChain.doFilter(request, response);log.warn("未能解密jwt");return;}//4.通过jwt获取用户信息,然后根据key获取redis中的jwtMap userInfo = JwtUtil.getUserInfo(jwt);Long userId = (Long) userInfo.get("userId");String redisJwt = (String) stringRedisTemplate.opsForValue().get("jwt" + userId.intValue());//5.核验两个jwtif (!jwt.equals(redisJwt)) {filterChain.doFilter(request, response);log.warn("redis里的和前端的不一致");return;}//6.给jwt续期stringRedisTemplate.opsForValue().set("jwt" + userId, jwt, 30, TimeUnit.DAYS);//7.往security容器中放登录凭证//实现步骤:获取security上下文类,往里面放一个凭证String username = (String) userInfo.get("username");UserDetails userDetails = myUserDetail.loadUserByUsername(username);UsernamePasswordAuthenticationToken upa = new UsernamePasswordAuthenticationToken(userDetails.getUsername(),userDetails.getPassword(),userDetails.getAuthorities());SecurityContextHolder.getContext().setAuthentication(upa);/*** 记得放行*/filterChain.doFilter(request, response);}
}

权限相关表设计

RBAC基于角色的访问控制

RBAC(Role-Based Access Control,基于角色的访问控制)模型是一种广泛用于访问控制的安全模型。它基于角色的概念,将权限授权和访问管理组织起来。

在RBAC模型中,有以下几个核心概念:

  • 角色(Role):角色是一组权限的集合,代表了用户在系统中所扮演的角色或身份。用户可以被分配一个或多个角色。
  • 权限(Permission):权限是对系统资源的操作权限。例如,读取、写入、执行等。权限定义了用户或角色可以进行的操作。
  • 用户(User):用户是系统的最终使用者,他们可以被分配一个或多个角色。
  • 资源(Resource):资源是受到访问控制保护的对象,可以是系统中的数据、功能、服务等。

数据库表设计

在这里插入图片描述

查询语句

SELECT 
ut.id,
ut.username,
ut.realname,
ut.password,
art.role_name,
art.role_note,
at.auth_name,
at.auth_urlFROM auth_user_tab ut
LEFT JOIN auth_role_user_tab arut ON arut.user_id=ut.id
LEFT JOIN auth_role_tab art ON art.role_id=arut.role_id
LEFT JOIN auth_role_privs_tab arpt ON arpt.rp_role=arut.role_id
LEFT JOIN auth_tab at ON at.auth_id=arpt.rp_privs

权限的注解式控制

配置打开注解

Spring Security 支持三套注解:

注解类型注解
jsr250 注解@DenyAll、@PermitAll、@RolesAllowed
secured 注解@Secured
prePost 注解@PreAuthorize、@PostAuthorize

使用什么注解在@EnableGlobalMethodSecurity开启,默认是关闭的,例如

@EnableWebSecurity
@EnableGlobalMethodSecurity(jsr250Enabled  = true,securedEnabled=true) //开启jsr250和secured注解
public class SecurityConfig extends WebSecurityConfigurerAdapter {
}

实际开发中最常用的写法 使用 @PreAuthorize(“hasRole(‘admin’)”)

在这里插入图片描述

使用注解控制权限

在这里插入图片描述

package com.tianju.controller;import com.baomidou.mybatisplus.extension.api.R;
import com.tianju.entity.GoodType;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;@RestController
@RequestMapping("/good/type")
public class GoodTypeController {@GetMapping@PreAuthorize("hasAnyAuthority('/good/query')")public String get(Integer id){return "查询的方法:"+id;}@PostMapping@PreAuthorize("hasAnyAuthority('/good/add')")public String add(GoodType goodType){return "新增商品的方法:"+goodType;}@DeleteMapping@PreAuthorize("hasAnyAuthority('/good/del')")public String deleteById(Integer id){return "删除的方法:"+id;}@PutMapping@PreAuthorize("hasAnyAuthority('/good/update')")public String updateById(GoodType goodType){return "修改的方法:"+goodType;}}

给不同的用户显示不同的页面

数据库表设计

在这里插入图片描述

查询语句

SELECTaut.username,t_menu.id,t_menu.name,t_menu.link,t_menu.parentid,t_menu.icon
FROM auth_user_tab AS autLEFT JOIN t_employee_menu ON aut.id = t_employee_menu.employeeIdLEFT JOIN t_menu ON t_employee_menu.menuId = t_menu.id

不同用户显示的效果

admin用户登录

在这里插入图片描述

peter用户登录

在这里插入图片描述


总结

1.Spring Security的使用,结合MySQL,Redis实现基于JWT的注解式的权限认证,并且可以实现给不同的用户显示不同的前端页面;
2.项目中的快速应用和使用,拦截器的设置,安全框架的配置;
3.权限表的设计,基于角色的访问控制RABC模型;
4.启动注解的配置,通过注解实现权限的控制;
5.给不同的用户显示不同的页面,相关的SQL以及前端页面;

附录:

1、前端页面

在这里插入图片描述

<template><el-container style="height: 100%"><el-header style="background-color: rgb(249, 195, 195);"></el-header><el-container><el-aside width="200px" style="background-color: rgb(241, 241, 202);"><el-col width="200px"><el-menurouterdefault-active="2"class="el-menu-vertical-demo"><el-submenu :index="menu.id+''" v-for="menu in menuList" :key="menu.id+''"><template slot="title"><i :class="menu.icon"></i><span>{{ menu.name }}</span></template><el-menu-item :index="cmenu.link" v-for="cmenu in menu.childrenMenu" :key="cmenu.id+''">{{ cmenu.name }}</el-menu-item></el-submenu></el-menu></el-col></el-aside><el-main style="background-color: rgb(182, 182, 231);"><router-view></router-view></el-main></el-container></el-container></template><script>export default{data() {return {// 定义一个数据,菜单从数据中循环出来table tr// 找出一级菜单和二级菜单循环体menuList:[{id:'1',name:'公共模块',icon:'el-icon-menu',childrenMenu:[{id:'2',name:'调查问卷',link:'/bookList'},{id:'3',name:'资料中心',link:'bcd'},{id:'4',name:'工资中心',link:'cde'},]},{id:'5',name:'业务目标',icon:'el-icon-document',childrenMenu:[{id:'5',name:'短期目标',link:'def'},{id:'6',name:'长期目标',link:'efg'},]},]};},methods: {// 查询用户拥有菜单queryUserMenu(){console.log("findMenu")this.$axios.get('/api/menu').then(response=>{let resp = response.dataconsole.log(resp)if (resp.resultCode.code==20000) {this.menuList = resp.results}})},},created(){this.queryUserMenu()}}
</script><style scoped></style>

2、MySQL数据库语句

/*Navicat Premium Data TransferSource Server         : 127.0.0.1Source Server Type    : MySQLSource Server Version : 80022Source Host           : 127.0.0.1:3306Source Schema         : auth_petTarget Server Type    : MySQLTarget Server Version : 80022File Encoding         : 65001Date: 06/11/2023 15:44:35
*/SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;-- ----------------------------
-- Table structure for auth_role_privs_tab
-- ----------------------------
DROP TABLE IF EXISTS `auth_role_privs_tab`;
CREATE TABLE `auth_role_privs_tab`  (`rp_id` bigint NOT NULL AUTO_INCREMENT COMMENT '角色权限的中间表relationship',`rp_role` bigint NULL DEFAULT NULL COMMENT '对应的是角色id',`rp_privs` bigint NULL DEFAULT NULL COMMENT '对应的权限id',`created` datetime NULL DEFAULT NULL,`updated` datetime NULL DEFAULT NULL,`create_by` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL,PRIMARY KEY (`rp_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 17 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of auth_role_privs_tab
-- ----------------------------
INSERT INTO `auth_role_privs_tab` VALUES (1, 1, 1, '2023-08-06 17:26:48', '2023-08-06 17:26:53', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (2, 1, 2, '2023-08-06 17:27:09', '2023-08-06 17:27:12', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (3, 1, 3, '2023-08-06 17:28:14', '2023-08-06 17:28:21', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (4, 1, 4, '2023-08-06 17:28:17', '2023-08-06 17:28:24', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (5, 1, 5, '2023-08-06 17:28:19', '2023-08-06 17:28:26', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (6, 1, 6, '2023-10-07 19:32:23', '2023-10-07 19:32:26', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (7, 1, 7, '2023-10-07 19:32:29', '2023-10-07 19:32:31', 'admin');
INSERT INTO `auth_role_privs_tab` VALUES (8, 2, 1, '2023-10-07 19:53:21', NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (9, 2, 2, '2023-10-07 19:53:25', NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (10, 2, 3, '2023-10-07 19:53:28', NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (11, 2, 4, '2023-10-07 19:53:30', NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (12, 5, 5, NULL, NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (13, 5, 6, NULL, NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (14, 5, 7, NULL, NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (15, 3, NULL, NULL, NULL, NULL);
INSERT INTO `auth_role_privs_tab` VALUES (16, 4, 1, NULL, NULL, NULL);-- ----------------------------
-- Table structure for auth_role_tab
-- ----------------------------
DROP TABLE IF EXISTS `auth_role_tab`;
CREATE TABLE `auth_role_tab`  (`role_id` bigint NOT NULL AUTO_INCREMENT COMMENT '角色的id,角色表',`role_name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '角色的name',`role_note` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '备注一下',`state` int NULL DEFAULT NULL COMMENT '状态,0启用,1删除',`created` datetime NULL DEFAULT NULL,`updated` datetime NULL DEFAULT NULL,`create_by` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL,PRIMARY KEY (`role_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 8 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of auth_role_tab
-- ----------------------------
INSERT INTO `auth_role_tab` VALUES (1, '老板Boss', '全部权限', 0, '2023-08-06 17:24:43', '2023-08-06 17:24:46', 'admin');
INSERT INTO `auth_role_tab` VALUES (2, '商品管理员工', '商品相关', 0, '2023-08-06 17:25:03', '2023-08-06 17:25:05', 'admin');
INSERT INTO `auth_role_tab` VALUES (3, '未实名用户', '无任何权限', 0, '2023-08-06 17:25:38', '2023-08-06 17:25:41', 'admin');
INSERT INTO `auth_role_tab` VALUES (4, '普通用户', '商品查询', 0, '2023-10-07 19:49:34', '2023-10-07 19:49:37', 'admin');
INSERT INTO `auth_role_tab` VALUES (5, '人事部门员工', '人事相关', 0, '2023-10-07 19:49:40', '2023-10-07 19:49:41', 'admin');
INSERT INTO `auth_role_tab` VALUES (7, '老板Boss1', NULL, 0, '2023-11-05 22:27:04', '2023-11-05 22:44:52', 'admin');-- ----------------------------
-- Table structure for auth_role_user_tab
-- ----------------------------
DROP TABLE IF EXISTS `auth_role_user_tab`;
CREATE TABLE `auth_role_user_tab`  (`id` int NOT NULL AUTO_INCREMENT COMMENT '角色,用户关联表,用户可能有多个角色',`user_id` int NULL DEFAULT NULL COMMENT '用户表的主键id',`role_id` int NULL DEFAULT NULL COMMENT '角色表的主键id',PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 6 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of auth_role_user_tab
-- ----------------------------
INSERT INTO `auth_role_user_tab` VALUES (1, 1, 1);
INSERT INTO `auth_role_user_tab` VALUES (2, 2, 2);
INSERT INTO `auth_role_user_tab` VALUES (3, 3, 5);
INSERT INTO `auth_role_user_tab` VALUES (4, 4, 4);
INSERT INTO `auth_role_user_tab` VALUES (5, 5, 3);-- ----------------------------
-- Table structure for auth_tab
-- ----------------------------
DROP TABLE IF EXISTS `auth_tab`;
CREATE TABLE `auth_tab`  (`auth_id` int NOT NULL AUTO_INCREMENT COMMENT '权限表的id',`auth_name` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '权限的名称',`auth_url` varchar(20) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '权限的url,安全框架用',PRIMARY KEY (`auth_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 8 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of auth_tab
-- ----------------------------
INSERT INTO `auth_tab` VALUES (1, '商品查询', '/good/query');
INSERT INTO `auth_tab` VALUES (2, '商品新增', '/good/add');
INSERT INTO `auth_tab` VALUES (3, '商品删除', '/good/del');
INSERT INTO `auth_tab` VALUES (4, '商品修改', '/good/update');
INSERT INTO `auth_tab` VALUES (5, '员工查询', '/emp/query');
INSERT INTO `auth_tab` VALUES (6, '员工新增', '/emp/add');
INSERT INTO `auth_tab` VALUES (7, '员工开除', '/emp/del');-- ----------------------------
-- Table structure for auth_user_tab
-- ----------------------------
DROP TABLE IF EXISTS `auth_user_tab`;
CREATE TABLE `auth_user_tab`  (`id` int NOT NULL AUTO_INCREMENT,`username` varchar(25) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '用户名',`realname` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '真实姓名',`password` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '密码',`tel` varchar(25) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '手机号',`gender` varchar(5) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '性别',`identity` varchar(25) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '身份证号',`create_time` datetime NULL DEFAULT NULL COMMENT '创建时间',`update_time` datetime NULL DEFAULT NULL COMMENT '修改时间',`operator` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '操作人',PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 6 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of auth_user_tab
-- ----------------------------
INSERT INTO `auth_user_tab` VALUES (1, 'admin', '超级管理', '123', '19800305334', '女', '433123456787', NULL, NULL, NULL);
INSERT INTO `auth_user_tab` VALUES (2, 'peter', '商品管理', '123', '18802229403', '男', '433123456788', NULL, NULL, NULL);
INSERT INTO `auth_user_tab` VALUES (3, 'shirley', '人事管理', '123', NULL, NULL, NULL, NULL, NULL, NULL);
INSERT INTO `auth_user_tab` VALUES (4, 'tom', '普通登陆用户', '123', NULL, NULL, NULL, NULL, NULL, NULL);
INSERT INTO `auth_user_tab` VALUES (5, 'test', '未实名认证', NULL, NULL, NULL, NULL, NULL, NULL, NULL);-- ----------------------------
-- Table structure for t_employee_menu
-- ----------------------------
DROP TABLE IF EXISTS `t_employee_menu`;
CREATE TABLE `t_employee_menu`  (`id_menu` int NOT NULL AUTO_INCREMENT,`employeeId` int NULL DEFAULT NULL COMMENT '员工id',`menuId` int NULL DEFAULT NULL COMMENT '菜单表id',PRIMARY KEY (`id_menu`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 31 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of t_employee_menu
-- ----------------------------
INSERT INTO `t_employee_menu` VALUES (1, 1, 1);
INSERT INTO `t_employee_menu` VALUES (2, 1, 2);
INSERT INTO `t_employee_menu` VALUES (3, 1, 3);
INSERT INTO `t_employee_menu` VALUES (4, 1, 4);
INSERT INTO `t_employee_menu` VALUES (5, 1, 5);
INSERT INTO `t_employee_menu` VALUES (6, 1, 6);
INSERT INTO `t_employee_menu` VALUES (7, 1, 7);
INSERT INTO `t_employee_menu` VALUES (9, 1, 9);
INSERT INTO `t_employee_menu` VALUES (10, 1, 10);
INSERT INTO `t_employee_menu` VALUES (11, 1, 11);
INSERT INTO `t_employee_menu` VALUES (12, 1, 12);
INSERT INTO `t_employee_menu` VALUES (13, 1, 13);
INSERT INTO `t_employee_menu` VALUES (14, 1, 14);
INSERT INTO `t_employee_menu` VALUES (15, 1, 15);
INSERT INTO `t_employee_menu` VALUES (16, 1, 16);
INSERT INTO `t_employee_menu` VALUES (17, 1, 17);
INSERT INTO `t_employee_menu` VALUES (18, 1, 18);
INSERT INTO `t_employee_menu` VALUES (19, 1, 19);
INSERT INTO `t_employee_menu` VALUES (20, 1, 20);
INSERT INTO `t_employee_menu` VALUES (21, 1, 21);
INSERT INTO `t_employee_menu` VALUES (22, 1, 22);
INSERT INTO `t_employee_menu` VALUES (23, 1, 23);
INSERT INTO `t_employee_menu` VALUES (24, 1, 24);
INSERT INTO `t_employee_menu` VALUES (25, 1, 25);
INSERT INTO `t_employee_menu` VALUES (27, 1, 27);
INSERT INTO `t_employee_menu` VALUES (29, 2, 1);
INSERT INTO `t_employee_menu` VALUES (30, 2, 2);-- ----------------------------
-- Table structure for t_menu
-- ----------------------------
DROP TABLE IF EXISTS `t_menu`;
CREATE TABLE `t_menu`  (`id` int NOT NULL AUTO_INCREMENT,`name` varchar(15) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL COMMENT '权限名称',`link` varchar(50) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL COMMENT '菜单链接',`parentid` int NULL DEFAULT NULL COMMENT '父级',`status` int NULL DEFAULT NULL COMMENT '1:正常 0:禁用',`percode` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL COMMENT '权限编码',`icon` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL COMMENT '图标',PRIMARY KEY (`id`) USING BTREE,INDEX `FK_ParentID`(`parentid`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 29 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;-- ----------------------------
-- Records of t_menu
-- ----------------------------
INSERT INTO `t_menu` VALUES (1, '系统管理', '', NULL, NULL, NULL, 'el-icon-location');
INSERT INTO `t_menu` VALUES (2, '商品类别', 'goodsType', 1, NULL, NULL, '');
INSERT INTO `t_menu` VALUES (3, '计量单位', 'unit', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (4, '仓库管理', 'warehouse', NULL, NULL, NULL, 'el-icon-s-data');
INSERT INTO `t_menu` VALUES (5, '原材料入库', 'rawMaterialList', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (6, '原材料领库', 'pickRawList', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (7, '订单管理', NULL, NULL, NULL, NULL, 'el-icon-s-tools');
INSERT INTO `t_menu` VALUES (9, '区域管理', 'district', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (10, '商品资料', 'goodsList', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (11, '供应商资料', 'supplier', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (12, '客户资料', 'customer', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (13, '仓库管理', 'warehouse', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (14, '部门管理', 'department', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (15, '员工管理', 'employee', 1, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (16, '成品入库', 'finishedPickRaw', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (17, '次品入库', 'defectiveGoodsIn', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (18, '成品发货', 'finishedGoodsOut', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (19, '次品发货', 'defectiveGoodsSend', 4, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (20, '财务管理', NULL, NULL, NULL, NULL, 'el-icon-s-data');
INSERT INTO `t_menu` VALUES (21, '应收款管理', 'income', 20, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (22, '应付款管理', 'expenses', 20, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (23, '数据统计', NULL, NULL, NULL, NULL, 'el-icon-s-data');
INSERT INTO `t_menu` VALUES (24, '仓库报表', 'storeStatistics', 23, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (25, '财务报表', 'financialStatistics', 23, NULL, NULL, NULL);
INSERT INTO `t_menu` VALUES (27, '订单查询', 'orderSearch', 7, NULL, NULL, NULL);SET FOREIGN_KEY_CHECKS = 1;

这篇关于登陆认证权限控制(2)—— 基于Spring security 安全框架的权限管理 注解式权限控制 RABC模型的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/358727

相关文章

springboot健康检查监控全过程

《springboot健康检查监控全过程》文章介绍了SpringBoot如何使用Actuator和Micrometer进行健康检查和监控,通过配置和自定义健康指示器,开发者可以实时监控应用组件的状态,... 目录1. 引言重要性2. 配置Spring Boot ActuatorSpring Boot Act

使用Java解析JSON数据并提取特定字段的实现步骤(以提取mailNo为例)

《使用Java解析JSON数据并提取特定字段的实现步骤(以提取mailNo为例)》在现代软件开发中,处理JSON数据是一项非常常见的任务,无论是从API接口获取数据,还是将数据存储为JSON格式,解析... 目录1. 背景介绍1.1 jsON简介1.2 实际案例2. 准备工作2.1 环境搭建2.1.1 添加

Java实现任务管理器性能网络监控数据的方法详解

《Java实现任务管理器性能网络监控数据的方法详解》在现代操作系统中,任务管理器是一个非常重要的工具,用于监控和管理计算机的运行状态,包括CPU使用率、内存占用等,对于开发者和系统管理员来说,了解这些... 目录引言一、背景知识二、准备工作1. Maven依赖2. Gradle依赖三、代码实现四、代码详解五

java如何分布式锁实现和选型

《java如何分布式锁实现和选型》文章介绍了分布式锁的重要性以及在分布式系统中常见的问题和需求,它详细阐述了如何使用分布式锁来确保数据的一致性和系统的高可用性,文章还提供了基于数据库、Redis和Zo... 目录引言:分布式锁的重要性与分布式系统中的常见问题和需求分布式锁的重要性分布式系统中常见的问题和需求

SpringBoot基于MyBatis-Plus实现Lambda Query查询的示例代码

《SpringBoot基于MyBatis-Plus实现LambdaQuery查询的示例代码》MyBatis-Plus是MyBatis的增强工具,简化了数据库操作,并提高了开发效率,它提供了多种查询方... 目录引言基础环境配置依赖配置(Maven)application.yml 配置表结构设计demo_st

在Ubuntu上部署SpringBoot应用的操作步骤

《在Ubuntu上部署SpringBoot应用的操作步骤》随着云计算和容器化技术的普及,Linux服务器已成为部署Web应用程序的主流平台之一,Java作为一种跨平台的编程语言,具有广泛的应用场景,本... 目录一、部署准备二、安装 Java 环境1. 安装 JDK2. 验证 Java 安装三、安装 mys

Springboot的ThreadPoolTaskScheduler线程池轻松搞定15分钟不操作自动取消订单

《Springboot的ThreadPoolTaskScheduler线程池轻松搞定15分钟不操作自动取消订单》:本文主要介绍Springboot的ThreadPoolTaskScheduler线... 目录ThreadPoolTaskScheduler线程池实现15分钟不操作自动取消订单概要1,创建订单后

JAVA中整型数组、字符串数组、整型数和字符串 的创建与转换的方法

《JAVA中整型数组、字符串数组、整型数和字符串的创建与转换的方法》本文介绍了Java中字符串、字符数组和整型数组的创建方法,以及它们之间的转换方法,还详细讲解了字符串中的一些常用方法,如index... 目录一、字符串、字符数组和整型数组的创建1、字符串的创建方法1.1 通过引用字符数组来创建字符串1.2

SpringCloud集成AlloyDB的示例代码

《SpringCloud集成AlloyDB的示例代码》AlloyDB是GoogleCloud提供的一种高度可扩展、强性能的关系型数据库服务,它兼容PostgreSQL,并提供了更快的查询性能... 目录1.AlloyDBjavascript是什么?AlloyDB 的工作原理2.搭建测试环境3.代码工程1.

Linux中chmod权限设置方式

《Linux中chmod权限设置方式》本文介绍了Linux系统中文件和目录权限的设置方法,包括chmod、chown和chgrp命令的使用,以及权限模式和符号模式的详细说明,通过这些命令,用户可以灵活... 目录设置基本权限命令:chmod1、权限介绍2、chmod命令常见用法和示例3、文件权限详解4、ch