当我们导入spring-security的包时,访问应用就会弹出要求登陆的界面。这个时候需要用户名和密码。
认识四个类或接口:
1.UserDetails,用户信息接口,存储用户的基本信息。已有的子类实现
org.springframework.security.core.userdetails.User
我们自己实现UserDetails,可以参考User。
2.PasswordEncoder 这是一个加密用户密码的接口,使用时需要注入到spring容器。首选BCryptPasswordEncoder,这个是源码里面有写的。
3.UserDetailsService,验证用户名接口,里面只有一个方法
UserDetails loadUserByUsername(String username) throws UsernameNotFoundException;
实现这个接口验证用户名存不存在,不存在抛出异常,存在返回一个UserDetails.
4.WebSecurityConfigurerAdapter类,webSecurity的适配器做一些配置的工作。
例:protected void configure(AuthenticationManagerBuilder auth) throws Exception{}方法,可以设置我们要用的UserDetailsService(验证用户名接口)的子类实现是哪一个。
还可以设置我们用的哪一个加密方式
// 自己实现的DetailsService
@Autowired
private MyUserDetailsService userDetailsService;
// 注入spring容器的PasswordEncoder子类实现
@Autowired
private PasswordEncoder passwordEncoder;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
// 设置用户名验证Service
auth.userDetailsService(userDetailsService)
// 设置用户密码加密方式
.passwordEncoder(passwordEncoder);
}
一、默认的密码
启动项目会控制台会生成一个密码,默认用户名是user。就可以登录了
二、配置用户名密码可以直接在springboot的配置文件配置。properties或者yml文件.
用配置的用户名密码就可以访问。
三、配置类设置密码新建配置类继承WebSecurityConfigurerAdapter类,实现他的方法设置用户名和密码。密码需要用
PasswordEncoder的子类加密。
设置三个值:
username:账号
password:密码
roles:权限字段
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.inMemoryAuthentication().withUser("123").password(new BCryptPasswordEncoder().encode("789")).roles("dsfd");
}
}
四、数据库读取账号密码
sql语句
CREATE TABLE users ( `id` int(11) NOT NULL AUTO_INCREMENT, `username` varchar(64) CHARACTER SET utf8 COLLATE utf8_general_ci DEFAULT NULL, `password` varchar(64) CHARACTER SET utf8 COLLATE utf8_general_ci DEFAULT NULL, PRIMARY KEY (`id`) USING BTREE ) ENGINE = InnoDB AUTO_INCREMENT = 2 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;
实体
import lombok.Data;
@Data
public class Users {
private String id;
private String username;
private String password;
}
mapper,我用的mybatis-plus
import com.baomidou.mybatisplus.core.mapper.baseMapper; import com.xx.job.entity.Users; import org.springframework.stereotype.Repository; @Repository public interface UserMapper extends baseMapper{ }
serice:需要写一个UserDetailsService的实现类,实现loadUserByUsername方法,实现逻辑数据库有没有这个用户名。
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.xx.job.entity.Users;
import com.xx.job.mapper.UserMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
@Service
public class MyUserDetailsService implements UserDetailsService {
@Autowired
private PasswordEncoder passwordEncoder;
@Autowired
private UserMapper userMapper;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
QueryWrapper queryWrapper = new QueryWrapper<>();
queryWrapper.eq("username",username);
Users users = userMapper.selectOne(queryWrapper);
if(users == null){
throw new UsernameNotFoundException("找不到用户名!");
}
return new User(username,passwordEncoder.encode(users.getPassword())
,AuthorityUtils.createAuthorityList("rolu"));
}
}
把密码加密接口PasswordEncoder注入到容器中
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
@Configuration
public class PasswordEncoderConfig {
@Bean
public PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}
}
WebSecurityConfigurerAdapter:security适配器配置我们写的service和密码加密方式。
import com.xx.job.service.MyUserDetailsService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.password.PasswordEncoder;
@Configuration
public class MyWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter {
@Autowired
private MyUserDetailsService userDetailsService;
@Autowired
private PasswordEncoder passwordEncoder;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder);
}
}
完成就可以通过数据库中的账号密码登录了。



