/*
Navicat Premium Data Transfer
Source Server : 本地
Source Server Type : MySQL
Source Server Version : 80013
Source Host : localhost:3306
Source Schema : test
Target Server Type : MySQL
Target Server Version : 80013
File Encoding : 65001
Date: 29/12/2022 11:46:09
*/
SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for users
-- ----------------------------
DROP TABLE IF EXISTS `users`;
CREATE TABLE `users` (
`id` int(11) NOT NULL,
`username` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL,
`password` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL,
`enable` tinyint(1) NULL DEFAULT NULL,
`roles` text CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '1admin 2user ',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;
-- ----------------------------
-- Records of users
-- ----------------------------
INSERT INTO `users` VALUES (1, 'admin', '123', 1, '1');
INSERT INTO `users` VALUES (2, 'user', '123', 1, '2');
INSERT INTO `users` VALUES (3, 'user1', '456', 1, '2');
SET FOREIGN_KEY_CHECKS = 1;
引入依赖:
<!--核心安全依赖--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-security</artifactId> </dependency>
实体类:
package com.example.security.pojo;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import java.io.Serializable;
import java.util.Collection;
import java.util.List;
import com.example.security.Enum.UserEnum;
import lombok.Data;
import org.springframework.security.access.annotation.Secured;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
/**
*
* @TableName users
*/
@TableName(value ="users")
@Data
public class Users implements UserDetails, Serializable {
/**
*
*/
@TableId
private Integer id;
/**
*
*/
private String username;
/**
*
*/
private String password;
/**
*
*/
private Integer enable;
/**
* 1admin 2user
*/
private UserEnum roles;
private List<GrantedAuthority> authorities;
@TableField(exist = false)
private static final long serialVersionUID = 1L;
@Override
public boolean equals(Object that) {
if (this == that) {
return true;
}
if (that == null) {
return false;
}
if (getClass() != that.getClass()) {
return false;
}
Users other = (Users) that;
return (this.getId() == null ? other.getId() == null : this.getId().equals(other.getId()))
&& (this.getUsername() == null ? other.getUsername() == null : this.getUsername().equals(other.getUsername()))
&& (this.getPassword() == null ? other.getPassword() == null : this.getPassword().equals(other.getPassword()))
&& (this.getEnable() == null ? other.getEnable() == null : this.getEnable().equals(other.getEnable()))
&& (this.getRoles() == null ? other.getRoles() == null : this.getRoles().equals(other.getRoles()));
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((getId() == null) ? 0 : getId().hashCode());
result = prime * result + ((getUsername() == null) ? 0 : getUsername().hashCode());
result = prime * result + ((getPassword() == null) ? 0 : getPassword().hashCode());
result = prime * result + ((getEnable() == null) ? 0 : getEnable().hashCode());
result = prime * result + ((getRoles() == null) ? 0 : getRoles().hashCode());
return result;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append(getClass().getSimpleName());
sb.append(" [");
sb.append("Hash = ").append(hashCode());
sb.append(", id=").append(id);
sb.append(", username=").append(username);
sb.append(", password=").append(password);
sb.append(", enable=").append(enable);
sb.append(", roles=").append(roles);
sb.append(", serialVersionUID=").append(serialVersionUID);
sb.append("]");
return sb.toString();
}
public void setAuthorities(List<GrantedAuthority> authorities) {
this.authorities = authorities;
}
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return this.authorities;
}
@Override
public boolean isAccountNonExpired() {
return true;
}
@Override
public boolean isAccountNonLocked() {
return true;
}
@Override
public boolean isCredentialsNonExpired() {
return true;
}
@Override
public boolean isEnabled() {
return true;
}
}
securityconfig配置类
package com.example.security.config;
import com.example.security.service.MyUserDetailsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
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.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.NoOpPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.provisioning.JdbcUserDetailsManager;
import javax.sql.DataSource;
/**
* @author:xxxxx
* @create: 2022-12-28 14:10
* @Description: SecurityConfig
*/
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
// @Bean
// public BCryptPasswordEncoder bCryptPasswordEncoder(){
// return new BCryptPasswordEncoder();
// }
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/admin/**")
.hasRole("ADMIN")
.antMatchers("/user/**")
.hasRole("USER")
.antMatchers("/visitor/**")
.permitAll()
.anyRequest()
.authenticated()
.and()
.formLogin()
.permitAll();
}
/***************************************在数据库中创建用户和角色****************************************************/
@Autowired
private MyUserDetailsService userDetailsService;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
//关联UserDetailsService对象
auth.userDetailsService(userDetailsService)
//对密码进行加密配置
// .passwordEncoder(bCryptPasswordEncoder());
.passwordEncoder(NoOpPasswordEncoder.getInstance());
}
}
UserDetailService
package com.example.security.service;
import com.example.security.mapper.UsersMapper;
import com.example.security.pojo.Users;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.stereotype.Service;
import org.springframework.util.Assert;
/**
* @author:xxxxx
* @create: 2022-12-28 16:44
* @Description:
*/
@Service
public class MyUserDetailsService implements UserDetailsService {
@Autowired
private UsersMapper userMapper;
@Override
public UserDetails loadUserByUsername(String username) {
// 从数据库尝试读取该用户
Users user = userMapper.findByUsername(username);
// 用户不存在,抛出异常
Assert.isTrue(user!=null,"用户不存在!");
// 将数据库形式的roles解析为UserDetails的权限集
// AuthorityUtils.commaSeparatedStringToAuthorityList是Spring Security
// 提供的用于将逗号隔开的权限集字符串切割成可用权限对象列表的方法
// 当然也可以自己实现,如用分号来隔开等,参考generateAuthorities
user.setAuthorities(AuthorityUtils.commaSeparatedStringToAuthorityList(String.valueOf(user.getRoles().getRole())));
return user;
}
}
UserMapper
package com.example.security.mapper;
import com.example.security.pojo.Users;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import org.apache.ibatis.annotations.Param;
/**
* @author Administrator
* @description 针对表【users】的数据库操作Mapper
* @createDate 2022-12-29 11:08:44
* @Entity com.example.security.pojo.Users
*/
public interface UsersMapper extends BaseMapper<Users> {
Users findByUsername(@Param("username") String username);
}
设置相应控制器权限
package com.example.security.controller;
/**
* @author:xxxxx
* @create: 2022-12-28 13:57
* @Description: HelloController
*/
import com.example.security.Enum.UserEnum;
import com.example.security.mapper.UsersMapper;
import com.example.security.pojo.Users;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.security.servlet.UserDetailsServiceAutoConfiguration;
import org.springframework.security.access.annotation.Secured;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/admin")
@Secured("ROLE_ADMIN")
public class AdminController {
@GetMapping("/hello")
public String hello() {
return "hello, admin";
}
}
UserEnum枚举类
package com.example.security.Enum;
import com.baomidou.mybatisplus.annotation.EnumValue;
import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonValue;
import lombok.Getter;
import java.lang.reflect.Array;
import java.util.Arrays;
@Getter
public enum UserEnum {
admin(1, "ROLE_ADMIN"),
user(2, "ROLE_USER");
@EnumValue
@JsonValue
private Integer code;
private String Role;
UserEnum(Integer code, String role) {
this.code = code;
Role = role;
}
@JsonCreator
public UserEnum getRoleByCode(Integer code) {
return Arrays.stream(values()).filter(item -> item.code == code).findFirst().orElse(null);
}
@JsonCreator
public UserEnum getByRole(String role) {
return Arrays.stream(values()).filter(item -> item.Role == role).findFirst().orElse(null);
}
}