Spring Boot整合Spring Security(二)自定义登录界面——formLogin()的配置

阅前提示

此文章基于Spring Security 6.0

一、Spring Boot中引入Spring Security

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>org.example</groupId>
    <artifactId>spring-security-demo</artifactId>
    <version>1.0-SNAPSHOT</version>

    <properties>
        <maven.compiler.source>19</maven.compiler.source>
        <maven.compiler.target>19</maven.compiler.target>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    </properties>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.0.1</version>
    </parent>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>
    </dependencies>
</project>

首先创建一个Spring Boot 项目,在dependency中引入Spring Security的依赖

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-security</artifactId>
</dependency>

之后启动项目,打开localhost:8080。可以看到,Spring Security基于Spring Boot的AutoConfigration,将对于主页的请求拦截,访问到了登录界面
在这里插入图片描述
在一般情况下,这个登录界面已经可以满足我们的需求了。但在大部分情况下,这个登录界面肯定是满足不了我们的要求的别问,问就是老板提的。所以我们需要自定义登录界面
默认情况下用户名是user
密码打印在控制台,可以看到类似这样的信息
在这里插入图片描述

二、配置formLogin()

先来创建Spring Security的配置类

@Configuration
@EnableWebSecurity
public class WebSecurityConfig {
	@Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        http
                .authorizeRequests((authorizeRequests) ->
                        authorizeRequests.requestMatchers("/js/**","/css/**").permitAll()
                                .anyRequest().authenticated()
                )
                .formLogin((formLogin) ->
                        formLogin
                                .usernameParameter("username")
                                .passwordParameter("password")
                                .loginPage("/login.html")
                                .loginProcessingUrl("/login")
                                .failureUrl("/login.html?error")
                                .permitAll()
                )
                .csrf(csrf -> csrf.disable());
        return http.build();
    }
}

以上代码的用途就是当请求路径匹配到 /js/** , /css/** 这类静态资源的时候,不做认证,直接放行,其他任何路径(anyRequest())都需要经过认证后才能放行。
以及本文的重点 formLogin() 的配置

  • usernameParamter()配置登录用户名参数名,默认就是 username
  • passwordParameter() 配置登录密码参数名,默认就是password
  • loginPage()配置登录界面的路径。默认GET方法的/login
  • loginProcessingUrl()配置登录按钮的路径。默认POST方法的/login
  • failureUrl()配置登录失败后访问的页面路径。默认/login?error
    最后别忘了permitAll(),或者将登录接口跟静态资源一起写到前面不需要认证的路径中。否则将会出现重定向过多错误。当你访问登录页面的时候需要认证,认证不通过,转到登录界面,循环,导致重定向过多错误

三、csrf配置

自Spring Security 4.0起,csrf防护默认开启,如果我们在默认的登录界面打开浏览器控制台,能看到如下代码
在这里插入图片描述
如果在自定义的界面中不配置_csrf参数,登录请求是会被拒绝的。这里我们先不用csrf将csrf配置成disable()

四、AuthenticationSuccessHandler与AuthenticationFailureHandler

随着传统项目不能再满足我们的需求(前后端分离,移动端流行,后端只需要提供数据),我们需要放弃重定向配置,自定义登录成功与失败后的操作

@Component
public class SecurityAuthenticationFailureHandler implements AuthenticationFailureHandler {
    @Override
    public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException {
        // TODO log user login failure and the number of login failure +1

        // return login failure message
        response.getWriter().println("{success:false,message:" + exception.getMessage() + "}");
    }
}
@Component
public class SecurityAuthenticationSuccessHandler implements AuthenticationSuccessHandler {

    @Override
    public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException {
        // TODO log user login success

        // return success message
        response.getWriter().println("{success:true,message:" + authentication.getName() + "}");
    }
}
@Configuration
@EnableWebSecurity
public class WebSecurityConfig {
    @Autowired
    private SecurityAuthenticationSuccessHandler securityAuthenticationSuccessHandler;

    @Autowired
    private SecurityAuthenticationFailureHandler securityAuthenticationFailureHandler;

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        http
                .authorizeRequests((authorizeRequests) ->
                        authorizeRequests.requestMatchers("/js/**","/css/**").permitAll()
                                .anyRequest().authenticated()
                )
                .formLogin((formLogin) ->
                        formLogin
                                .usernameParameter("username")
                                .passwordParameter("password")
                                .loginProcessingUrl("/login")
                                .successHandler(securityAuthenticationSuccessHandler)
                                .failureHandler(securityAuthenticationFailureHandler)
                                .permitAll()
                )
                .csrf(csrf -> csrf.disable());
        return http.build();
    }
}

前后端分离的项目中loginPage()都不需要,只需要配置successHandler()和failureHandler()并实现AuthenticationSuccessHandler和AuthenticationFailureHandler接口

  • 2
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值