注重版权,转载请注明原作者和原文链接
作者:码农BookSea
原文链接: https://blog.csdn.net/bookssea/article/details/109262109
新建表,主键id全部都是自增。
用户user2表
CREATE TABLE user2 ( uid int(11) NOT NULL AUTO_INCREMENT,
username varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci
NULL DEFAULT NULL, password varchar(255) CHARACTER SET utf8
COLLATE utf8_general_ci NULL DEFAULT NULL, PRIMARY KEY (uid) USING
BTREE ) ENGINE = InnoDB AUTO_INCREMENT = 11 CHARACTER SET = utf8
COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
角色role2表,指定了2个角色
CREATE TABLE role2 ( rid int(11) NOT NULL AUTO_INCREMENT,
role varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL
DEFAULT NULL, PRIMARY KEY (rid) USING BTREE ) ENGINE = InnoDB
AUTO_INCREMENT = 3 CHARACTER SET = utf8 COLLATE = utf8_general_ci
ROW_FORMAT = Dynamic;
用户角色关系user2_role2表
CREATE TABLE user2_role2 ( id int(11) NOT NULL AUTO_INCREMENT,
uid int(11) NULL DEFAULT NULL, rid int(11) NULL DEFAULT NULL,
PRIMARY KEY (id) USING BTREE ) ENGINE = InnoDB AUTO_INCREMENT = 10
CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
创建entity实体类
User类
@Data
public class User {
private Integer uid;
private String username;
private String password;
}
Role类
@Data
public class Role {
private Integer rid;
private String role;
}
创建DTO类
因为用户和角色是多对多关系,需要在用户中含有角色的对象,角色中含有用户的对象,创建DTO类而不再entity类中添加,是因为entity类属性是和表字段一一对应的,一般不推荐在entity类中添加与表字段无关的属性。
新建dto包,在包下创建如下类:
– 添加1个用户 INSERT INTO user2 VALUES (1, ‘user’, ‘user123’);
– 添加2个角色 INSERT INTO role2 VALUES (1, ‘user’); INSERT INTO role2 VALUES (2, ‘admin’);
– 1个用户,拥有2个角色 INSERT INTO user2_role2 VALUES (1, 1, 1); INSERT INTO user2_role2 VALUES (2, 1, 2);
UserDTO类
// 注意,多对多不要用@Data,因为ToString会相互调用,导致死循环
@Setter
@Getter
public class UserDTO extends User {
private Set<Role> roles;
}
RoleDTO类(目前用不到,可不建)
// 注意,多对多不要用@Data,因为ToString会相互调用,导致死循环
@Setter
@Getter
public class RoleDTO extends Role {
private Set<User> users;
}
添加UserMapper.java类
@Mapper
@Repository
public interface UserMapper {
// 查询用户
UserDTO selectUserByUsername(@Param("username") String username);
}
从数据库中获取用户、密码进行登录:
添加MyUserDetailsService.java,实现UserDetailsService,重写loadUserByUsername方法:
@Component
public class MyUserDetailsService implements UserDetailsService {
@Autowired
private UserService userService;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
UserDTO user = userService.getUser(username);
if (user == null) {
throw new UsernameNotFoundException("用户不存在");
}
// 添加用户拥有的多个角色
List<GrantedAuthority> grantedAuthorities = new ArrayList<>();
Set<Role> roles = user.getRoles();
for (Role role : roles) {
grantedAuthorities.add(new SimpleGrantedAuthority("ROLE_" + role.getRole()));
}
return new User(
user.getUsername(),
// 数据库中密码没加密,需加密
new BCryptPasswordEncoder().encode(user.getPassword()),
grantedAuthorities
);
}
}
添加WebSecurityConfig.java,继承WebSecurityConfigurerAdapter,重写configure(AuthenticationManagerBuilder auth)方法:
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private MyUserDetailsService userDetailsService;
@Bean
public PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth
.userDetailsService(userDatailService)
.passwordEncoder(passwordEncoder());
}
}
重新启动,可以使用user/user123登录了。
查看登录用户信息
要查看登录用户信息,我们可以在UserController中添加方法:
@RestController
public class UserController {
@Autowired
private UserService userService;
@GetMapping("/get-user")
public UserDTO getUser(@RequestParam String username){
return userService.getUser(username);
}
/**
* 查看登录用户信息
*/
@GetMapping("/get-auth")
public Authentication getAuth(){
return SecurityContextHolder.getContext().getAuthentication();
}
}