三、Spring Reactive Security从数据库查询用户

要从数据库查询用户,只需要配置数据库连接。同时实现的用户要实现org.springframework.security.core.userdetails.UserDetails接口。从数据库查询用户要实现org.springframework.security.core.userdetails.ReactiveUserDetailsService接口。

 

首先建表:

create table t_user(
id_key bigserial primary key,
username varchar(30),
password varchar(100),
Account_Non_Expired bool,
Account_Non_Locked bool,
Credentials_Non_Expired bool,
enabled bool
);

create table t_roles(
id_key bigserial primary key,
role_name varchar(20),
role_desc varchar(50)
);

create table t_user_roles(
id_key bigserial primary key,
user_id int8,
role_id int8
);

数据库选用Postgresql。t_user_roles是用户和角色关联表。

 

添加依赖:


com.baomidou
mybatis-plus-boot-starter
3.4.2


org.postgresql
postgresql


org.projectlombok
lombok

 

application.properties配置数据库连接:

spring.datasource.driver-class-name=org.postgresql.Driver
spring.datasource.url=jdbc:postgresql://localhost:5432/postgres
spring.datasource.username=postgres
spring.datasource.password=xxxx

 

启动类配置mapper扫描路径:

@MapperScan("com.example.mapper")

 

添加用户实体类:

@AllArgsConstructor
@NoArgsConstructor
@ToString
@Builder
@TableName("t_user")
public class UserEntity implements UserDetails {

/**
* 主键
*/
@TableId(type = IdType.AUTO)
private Long idKey;

/**
* 用户名
*/
private String username;

/**
* 密码
*/
private String password;

/**
* 账户是否过期
*/
private Boolean accountNonExpired;

/**
* 账户是否被锁定
*/
private Boolean accountNonLocked;

/**
* 密码是否过期
*/
private Boolean credentialsNonExpired ;

/**
* 是否启用
*/
private Boolean enabled;

@TableField(exist = false)
private Collection authorities;

public Long getIdKey() {
return idKey;
}

public void setIdKey(Long idKey) {
this.idKey = idKey;
}

public void setUsername(String username) {
this.username = username;
}

public void setPassword(String password) {
this.password = password;
}

public void setAccountNonExpired(Boolean accountNonExpired) {
this.accountNonExpired = accountNonExpired;
}

public void setAccountNonLocked(Boolean accountNonLocked) {
this.accountNonLocked = accountNonLocked;
}

public void setCredentialsNonExpired(Boolean credentialsNonExpired) {
this.credentialsNonExpired = credentialsNonExpired;
}

public void setEnabled(Boolean enabled) {
this.enabled = enabled;
}

public void setAuthorities(Collection authorities) {
this.authorities = authorities;
}

@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return null;
}

@Override
public String getPassword() {
return password;
}

@Override
public String getUsername() {
return username;
}

@Override
public boolean isAccountNonExpired() {
return accountNonExpired;
}

@Override
public boolean isAccountNonLocked() {
return accountNonLocked;
}

@Override
public boolean isCredentialsNonExpired() {
return credentialsNonExpired;
}

@Override
public boolean isEnabled() {
return enabled;
}
}

添加角色类:

@ToString
public class SimpleGrantedAuthority implements GrantedAuthority {

private String authority;

public SimpleGrantedAuthority(String authority) {
this.authority = authority;
}

@Override
public String getAuthority() {
return authority;
}
}

添加角色实体类:

@AllArgsConstructor
@NoArgsConstructor
@Data
@Builder
@TableName("t_roles")
public class RoleEntity {

/**
* 主键
*/
@TableId(type = IdType.AUTO)
private Long idKey;

/**
* 角色名
*/
private String roleName;

/**
* 角色描述
*/
private String roleDesc;
}

添加关联实体类:

@AllArgsConstructor
@NoArgsConstructor
@Data
@Builder
@TableName("t_user_roles")
public class UserRoleRelationEntity {

/**
* 主键
*/
@TableId(type = IdType.AUTO)
private Long idKey;

private Long userId;

private Long roleId;
}

添加mapper:

public interface RoleMapper extends BaseMapper {
}

public interface UserMapper extends BaseMapper {
}

public interface UserRoleRelationMapper extends BaseMapper {
}

 

添加密码加密器:

MyReactiveSecurityConfig.class

@Bean
public PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}

 

添加ReactiveUserDetailsService实现类:

@Service
@Slf4j
public class MyReactiveUserDetailsService implements ReactiveUserDetailsService {
@Autowired
private UserMapper userMapper;

@Autowired
private RoleMapper roleMapper;
@Autowired
private UserRoleRelationMapper userRoleRelationMapper;

@Override
public Mono findByUsername(String username) {

log.info("用户名:{}从数据库查询用户", username);

UserEntity userEntity = userMapper.selectOne(Wrappers.lambdaQuery(UserEntity.class)
.eq(UserEntity::getUsername, username));

if (userEntity == null) {
log.info("用户名:{}从数据库未查询到用户", username);
return Mono.empty();
}

List userRoleRelationEntities = userRoleRelationMapper.selectList(Wrappers.lambdaQuery(UserRoleRelationEntity.class)
.eq(UserRoleRelationEntity::getUserId, userEntity.getIdKey()));
log.info("用户名:{}从数据库查询角色:{}", username,userRoleRelationEntities);
if (!CollectionUtils.isEmpty(userRoleRelationEntities)) {
List roleEntities = roleMapper.selectList(Wrappers.lambdaQuery(RoleEntity.class)
.in(RoleEntity::getIdKey, userRoleRelationEntities.stream().map(UserRoleRelationEntity::getRoleId).collect(Collectors.toList())));

List roles = roleEntities.stream().map(RoleEntity::getRoleName).map(SimpleGrantedAuthority::new).collect(Collectors.toList());
userEntity.setAuthorities(roles);

log.info("用户名:{}从数据库查询到用户:{}", username,userEntity);
}
return Mono.just(userEntity);
}
}

 

添加新增用户测试:

@Autowired
private UserMapper userMapper;

@Autowired
private RoleMapper roleMapper;
@Autowired
private UserRoleRelationMapper userRoleRelationMapper;

@Autowired
private PasswordEncoder passwordEncoder;

@Test
public void test() {
addUser("USER","普通用户", "user","123");

addUser("ADMIN","管理员","admin","123");
}

private void addUser(String roleName,String roleDesc,String username,String password) {
RoleEntity role = RoleEntity.builder()
.roleDesc(roleDesc)
.roleName(roleName)
.build();

roleMapper.insert(role);

UserEntity user = UserEntity.builder().username(username)
.password(passwordEncoder.encode(password))
.accountNonExpired(true)
.accountNonLocked(true)
.enabled(true)
.credentialsNonExpired(true)
.build();

userMapper.insert(user);

UserRoleRelationEntity entity = UserRoleRelationEntity.builder()
.userId(user.getIdKey())
.roleId(role.getIdKey())
.build();

userRoleRelationMapper.insert(entity);

}

posted @ 2023-06-06 20:29  shigp1  阅读(194)  评论(0)    收藏  举报