首页 > 技术文章 > Spring Security基本用法

javakangkang 2020-11-26 23:34 原文

本质:获取用户名密码验证登陆状态,密码匹配通过,查询该用户的权限角色数据,放到内存中,设置放行路径,Controller再拦截较验 

基于数据库的用户角色配置

1,创建 UserService

定义的 UserService 实现 UserDetailsService 接口,并实现该接口中的 loadUserByUsername 方法,该方法将在用户登录时自动调用。

loadUserByUsername 方法的参数就是用户登录时输入的用户名,通过用户名去数据库中查找用户:

    • 如果没有查找到用户,就抛出一个账户不存在的异常。
    • 如果查找到了用户,就继续查找该用户所具有的角色信息,并将获取到的 user 对象返回,再由系统提供的 DaoAuthenticationProvider类去比对密码是否正确。
@Service
public class UserService implements UserDetailsService {
    @Autowired
    private UserMapperDao userMapperDao;
    @Autowired
    private PasswordEncoder passwordEncoder;

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        User user = userMapperDao.loadUserByUsername(username); //查询登陆用户的数据库信息
          if (user == null) {
            throw new UsernameNotFoundException("账户不存在!");
        }
         // 我的数据库用户密码没加密,这里手动设置
        String encodePassword = passwordEncoder.encode(user.getPassword());
        System.out.println("加密后的密码:" + encodePassword);
        user.setPassword(encodePassword);
        List<Role> userRoles = userMapperDao.getUserRolesByUid(user.getId());
        user.setUserRoles(userRoles);
        return user;
    }
}

2.配置 Spring Security

 Spring Security 大部分配置与前文一样,只不过这次没有配置内存用户,而是将刚刚创建好的 UserService 配置到 AuthenticationManagerBuilder 中。

@Configuration
public class MyWebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private UserService userService;


    // 指定密码的加密方式
    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }

    // 配置用户及其对应的角色
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userService);
    }

    // 配置基于内存的 URL 访问权限
    @Override
    protected  void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests() // 开启 HttpSecurity 配置
                .antMatchers("/admin/**").hasRole("ADMIN") // admin/** 模式URL必须具备ADMIN角色
                .antMatchers("/user/**").access("hasAnyRole('ADMIN','USER')") // 该模式需要ADMIN或USER角色
                .antMatchers("/db/**").access("hasRole('ADMIN') and hasRole('DBA')") // 需ADMIN和DBA角色
                .anyRequest().authenticated() // 用户访问其它URL都必须认证后访问(登录后访问)
                .and().formLogin().loginProcessingUrl("/login").permitAll() // 开启表单登录并配置登录接口
                .and().csrf().disable(); // 关闭csrf
    }

3.运行测试

@RestController
public class HelloController {
 
    @GetMapping("/admin/hello")
    public String admin() {
        return "hello admin";
    }
 
    @GetMapping("/user/hello")
    public String user() {
        return "hello user";
    }
    @GetMapping("/db/hello")
    public String db() {
        return "hello db";
    }
 
    @GetMapping("/hello")
    public String hello() {
        return "hello";
    }
}

 参考https://www.cnblogs.com/dw3306/p/12751373.html

https://www.cnblogs.com/youngdeng/p/12869018.html

推荐阅读