从永远到永远-SpringSecurity(一)

1.HTTP Basic模式

1、代码

配置类继承WebSecurityConfigurerAdapter,并重写其中一个方法:

@Configuration
public class HttpBasicSecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.httpBasic()
                .and()
                .authorizeRequests()
                .anyRequest()
                .authenticated();
    }
}

测试:
访问login.html,被拦截,要求先登录。用户名为框架默认,密码启动项目时生成:在这里插入图片描述

在这里插入图片描述

2、配置用户名及密码

配置文件中,可以指定密码。

  security:
    user:
      password: admin
      name: administrator

3、特点

其验证时,发送get请求。在请求头携带了此验证信息,其实就是用户名密码base64加密后的字符串。非常容易被破解,不安全。
在这里插入图片描述
解密:
在这里插入图片描述

2.HTTP FormLogin模式

1、demo

protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable()//防止跨站csrf攻击
                .formLogin()
                .loginPage("/login.html")//设置登陆页面
                .loginProcessingUrl("/login")//form表单对应action地址
                .usernameParameter("username")//form表单输入的用户名对应的名称,默认username
                .passwordParameter("password")
                .defaultSuccessUrl("/index")//登录成功默认跳转路径
        .and()
                .authorizeRequests()
                .antMatchers("/login.html","/login").permitAll()//不需要验证就能访问的资源
                .antMatchers("/biz1","/biz2").hasAnyAuthority("ROLE_user","ROLE_admin")//admin user角色访问 ROLE_是ss框
                .antMatchers("/syslog","/sysuser").hasAnyAuthority("ROLE_admin")//admin 角色才可访问
                .anyRequest().authenticated();
                //hasAnyAuthority("ROLE_user","ROLE_admin")等价于hasAnyRole("user","admin"),角色是一种特殊的权限。
    }
    @Override
    public void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()//内存里面存储用户的身份认证和授权信息。
                .withUser("user")
                .password(passwordEncoder().encode("123456"))
                .roles("user")//方法用于指定用户的角色,一个用户可以有多个角色
        .and()
                .withUser("admin")
                .password(passwordEncoder().encode("123456"))
                .roles("admin")
        .and()
                .passwordEncoder(passwordEncoder());
    }
    @Bean
    public PasswordEncoder passwordEncoder(){
        return new BCryptPasswordEncoder();
    }
    @Override
    public void configure(WebSecurity web) {
        //将项目中静态资源路径开放出来
        web.ignoring()
                .antMatchers( "/css/**", "/fonts/**", "/img/**", "/js/**");//TODO 不知道为什么上边配置不起作用
    }

2、测试(略)

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
其他页面也能正常访问。
同理,测试user用户。

3、一个bug

本来,我可以过得很快乐,但是bug害了我。
输入用户名密码,点击登录,访问login时,报302的问题。
我被这个问题坑了一天,查了n多资料都没解决。其实这个不能算是Spring Security的问题。而是因为:
在这里插入图片描述

启动项目,访问localhost:8888/index.html。会被成功重定向到login.html,
输入验证信息,访问login时302,之后应该跳转的index.html页面404。

因为其机制是当用户名、密码验证通过后,其默认是重定向到你之前访问的地址。
index.html这个页面,是放在templates目录下的(跟着教程使用了freemarker
模板),必须通过controller访问。所以,根本就不是SpringSecurity的问题!

4、自定义认证成功处理handler

前边是直接定义了认证后(成功或失败)跳转的页面,现在自定义成功和失败的处理逻辑。

1、认证成功handler组件:

@Component
public class SuccessAuthenticationHandler extends SavedRequestAwareAuthenticationSuccessHandler {
    @Value("${spring.security.loginType}")
    private String loginType;//以什么形式返回,是给json数据提示还是返回html页面
    private static ObjectMapper objectMapper = new ObjectMapper();//对象和json字符串转换,@Response Body底层也是用它

    @Override
    public void onAuthenticationSuccess(HttpServletRequest request,
                                        HttpServletResponse response,
                                        Authentication authentication) throws IOException, ServletException {
        if ("JSON".equalsIgnoreCase(loginType)){
            response.setContentType("application/json;charset=utf-8");
            response.getWriter().write(objectMapper.writeValueAsString(R.success("/index")));
        }else{
            //跳转到登陆前请求的页面
            super.onAuthenticationSuccess(request,response,authentication);
        }
    }
}

同时需要调整此处:
在这里插入图片描述

2.认证失败handler组件

@Component
public class FailureAuthenticationHandler extends SimpleUrlAuthenticationFailureHandler {
    private static ObjectMapper objectMapper= new ObjectMapper();
    @Value("${spring.security.loginType}")
    private String loginType;
    @Override
    public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException {
        if ("JSON".equalsIgnoreCase(loginType)){
            response.setContentType("application/json;charset=utf-8");
            response.getWriter().write(objectMapper.writeValueAsString(R.error(
                    new CustomException(CustomExceptionType.USER_INPUT_ERROR,"用户信息异常,验证失败!")
            )));
        }else{
            super.onAuthenticationFailure(request,response,exception);
        }
    }
}

同样需要配置失败handler
在这里插入图片描述

测试通过,目前因为页面没有改造,还是页面跳转的形式。所以,目前认证成功或失败都是返回页面。
在这里插入图片描述

3、json格式返回数据

如果我们是以json返回数据,而不是HTML的话,就要稍微改造下页面才能测试。
这是之前的页面
在这里插入图片描述
修改,使其发送Ajax请求:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>formLogin登录方式的登录页</title>
    <script src="https://cdn.staticfile.org/jquery/1.12.3/jquery.min.js"></script>
</head>
<body>
<h1>scbg业务系统登录</h1>
<form action="/login" method="post">
    <span>用户名称:</span><input type="text" name="username" id="username"/> <br>
    <span>用户密码:</span><input type="password" name="password" id="password"/> <br>
    <input type="button" onclick="login()" value="登录">
</form>
<script>
    function login() {
        let username= $("#username").val();
        let password= $("#password").val();
        if (username ===""|| password ===""){
            alert("username or password cannot be empty!")
            return false;
        }
        $.ajax({
            type: "POST",
            url: "/login",
            data: {
                "username":username,
                "password":password
            },
            success: function (result) {
                if (result.isok){
                    let s = JSON.stringify(result);
                    alert("认证成功返回结果::"+s)
                    location.href= result.data
                }else{
                    alert("result:"+result.message)
                }
            },
            error:function (e) {
                console.log(e.responseText)
            }
        })
    }
</script>
</body>
</html>

测试:
认证成功
在这里插入图片描述
在这里插入图片描述
认证失败

在这里插入图片描述

5.session的管理

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
一分钟后,超时,回到登录页面
在这里插入图片描述
再次登录,sessionID已经变化
在这里插入图片描述

6、cookie的管理(略)

©️2020 CSDN 皮肤主题: 大白 设计师:CSDN官方博客 返回首页