Spring Security与SpringBoot2的整合
Spring Security安全框架的使用主要是通过写配置类来实现相关的安全操作
Spring Security的配置类要继承WebSecurityConfigurerAdapter

一、设置通过表单页面进行登录

因为使用表单登录所以需要对登录页面进行相应的配置,也就只是Controller的一个方法和一个页面

  1. @RequestMapping("/login")
  2. public String login() {
  3. return "login";
  4. }

login.html页面,这里使用的是thymeleaf模板引擎,用到了th的语法

action必须是/login

  1. <h1>权限控制登陆系统</h1>
  2. <form th:action="@{/login}" method="post">
  3. <span>用户名称</span><input type="text" name="username"/> <br>
  4. <span>用户密码</span><input type="password" name="password"/> <br>
  5. <input type="submit" value="登陆">
  6. </form>

二、设置异常页面

Spring Boot整合Spring Security需要配置一下异常页面,不然出现权限不足时的页面太捞了

写一个配置类就行了

@Configuration
public class WebServerAutoConfiguration {
    @Bean
    public ConfigurableServletWebServerFactory webServerFactory() {
        TomcatServletWebServerFactory factory = new TomcatServletWebServerFactory();
        ErrorPage errorPage400 = new ErrorPage(HttpStatus.BAD_REQUEST, "/error/400");
        ErrorPage errorPage401 = new ErrorPage(HttpStatus.UNAUTHORIZED, "/error/401");
        ErrorPage errorPage403 = new ErrorPage(HttpStatus.FORBIDDEN, "/error/403");
        ErrorPage errorPage404 = new ErrorPage(HttpStatus.NOT_FOUND, "/error/404");
        ErrorPage errorPage415 = new ErrorPage(HttpStatus.UNSUPPORTED_MEDIA_TYPE, "/error/415");
        ErrorPage errorPage500 = new ErrorPage(HttpStatus.INTERNAL_SERVER_ERROR, "/error/500");
        factory.addErrorPages(errorPage400, errorPage401, errorPage403, errorPage404, errorPage415, errorPage500);
        return factory;
    }
}

这里实现的功能是添加admin和user两个用户,admin能进行查询订单、添加订单、更新订单、删除订单的操作,而user用户只能查询和添加访问另外两个则会显示权限不足

编写配置类

  • 该配置里继承WebSecurityConfigurerAdapter 并添加@Configuration @EnableWebSecurity 这两个注解

  • configure(AuthenticationManagerBuilder auth) 方法里使用 auth.inMemoryAuthentication().withUser(“admin”).password(“123456”)是用来配置一个账号密码然后.authorities用来给该用户配置权限的别名

  • configure(HttpSecurity http)方法里使用http.authorizeRequests().antMatchers(“/showOrder”).hasAnyAuthority(“showOrder”)给url路径为/showOrder配置一个权限别名为showOrder与上面的方法给用户配置权限对应配置完成权限之后.antMatchers(“/login”).permitAll()是进行登录页面的配置,然后.antMatchers(“order“)是对Spring Security所管辖的权限控制的url范围,这里的意思是url中带有order的它都管,一般可以设置为/** 就是所有路径了

  • 后面使用.formLogin().loginPage(“/login”)是让Spring Security以表单验证的形式登录/login是登录页面的url需要在Controller层里写好相应的方法,下面还有个以httpBasic的方式登录,那种方式是项目运行首页会弹出一个框进行输入账号密码,太捞了这里就不用了

  • NoOpPasswordEncoder方法用@Bean 注解是让Spring Security允许使用未加密的密码进行登录

主要代码如下

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    //配置用户信息和权限
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        //添加admin账号并配置权限
        auth.inMemoryAuthentication().withUser("admin").password("123456")
                .authorities("showOrder", "addOrder", "updateOrder", "deleteOrder");
        //添加user账号并配置权限
        auth.inMemoryAuthentication()
            .withUser("user").password("123456").authorities("showOrder", "addOrder");
    }

    @Override
    //配置拦截请求资源
    protected void configure(HttpSecurity http) throws Exception {
        //如何权限控制 给每一条路径分配一个权限名称 账号只要管理该名称 就可以访问权限
        http.headers().frameOptions().disable();
        http.authorizeRequests()
                .antMatchers("/showOrder").hasAnyAuthority("showOrder")
                .antMatchers("/addOrder").hasAnyAuthority("addOrder")
                .antMatchers("/updateOrder").hasAnyAuthority("updateOrder")
                .antMatchers("/deleteOrder").hasAnyAuthority("deleteOrder")
                .antMatchers("/login").permitAll()
                .antMatchers("**order**")
                .fullyAuthenticated()
                .and().formLogin().loginPage("/login").and().csrf().disable();

        //httpBasic模式
        //http.authorizeRequests().antMatchers("/**").fullyAuthenticated().and().httpBasic();
    }

    // SpringBoot2.0抛弃了原来的NoOpPasswordEncoder,要求用户保存的密码必须要使用加密算法后存储,这里为了学习了解所以配置此方法用来进行非加密的密码进行登录
    @Bean
    public static NoOpPasswordEncoder passwordEncoder() {
        // 在登录验证的时候Security会将获得的密码在进行编码后再和数据库中加密后的密码进行对比
        return (NoOpPasswordEncoder) NoOpPasswordEncoder.getInstance();
    }

}

这样就实现了写死的用户权限配置

controller层

@RequestMapping("/order")
public class OrderController {

    @GetMapping("/showOrder")
    public String showOrder() {
        return "查询订单";
    }

    @PostMapping("/addOrder")
    public String addOrder() {
        return "添加订单";
    }

    @PostMapping("/updateOrder")
    public String updateOrder() {
        return "修改订单";
    }

    @GetMapping("/deleteOrder")
    public String deleteOrder() {
        return "删除订单";
    }

}

根据配置类的配置,admin用户可以访问四个接口,而user用户只能访问查询和添加订单的接口