面试篇:Spring Security

基础概念

什么是Spring Security?

Spring Security 是 Spring 家族中用于提供 认证(Authentication)和授权(Authorization) 的安全框架。它是高度可定制的安全解决方案,支持 Web 安全、方法级安全、OAuth2、JWT 等主流安全机制。


Spring Security 的核心功能有哪些?

  1. 认证机制:用户名密码验证、基于 Token 的认证(如 JWT)。

  2. 授权机制:基于角色或权限控制用户访问资源。

  3. 会话管理:支持登录、登出、会话失效处理等。

  4. 防止攻击

    • CSRF(跨站请求伪造)防护

    • XSS(跨站脚本攻击)防护

    • 会话固定攻击防护

  5. 方法级安全 :使用注解如 @PreAuthorize 控制方法访问。

  6. 自定义扩展能力强:支持自定义用户服务、认证逻辑、权限模型。


Spring Security 与 Shiro 有何区别?

对比点 Spring Security Apache Shiro
所属体系 Spring 全家桶 独立安全框架
功能丰富度 非常丰富,全面支持 OAuth、JWT 等 功能较轻量,但易于上手
与Spring集成 原生集成 需手动配置
扩展性 极强,适合大型项目 适中,适合中小型项目

认证与授权

Spring Security 的认证流程是怎样的?

认证流程主要包括以下步骤:

  1. 用户提交用户名和密码。

  2. UsernamePasswordAuthenticationFilter 拦截请求,构造 Authentication 对象。

  3. AuthenticationManager 调用 UserDetailsService 获取用户信息。

  4. 校验密码是否匹配(通过 PasswordEncoder)。

  5. 验证成功后,生成 Authentication 对象放入 SecurityContextHolder 中。

  6. 后续请求将携带认证信息,供授权模块判断访问权限。


什么是UserDetails和UserDetailsService?

  • UserDetails:表示用户的核心信息,如用户名、密码、权限等。

  • UserDetailsService:用于根据用户名加载用户信息,是认证过程的关键接口。

复制代码
public class CustomUserDetailsService implements UserDetailsService {
    @Override
    public UserDetails loadUserByUsername(String username) {
        // 查询数据库返回 UserDetails
        return new User(...);
    }
}

如何自定义登录认证逻辑?

  1. 实现 UserDetailsService 加载用户信息。

  2. 注入 AuthenticationManager 和自定义 PasswordEncoder

  3. 可重写 configure(HttpSecurity http) 添加自定义登录 URL、登录成功/失败处理器等。

复制代码
http.formLogin()
    .loginPage("/login")
    .successHandler(mySuccessHandler)
    .failureHandler(myFailureHandler);

如何实现基于角色或权限的访问控制?

Spring Security 支持三种授权方式:

  1. 基于 URL 的权限控制
复制代码
http.authorizeRequests()
    .antMatchers("/admin/**").hasRole("ADMIN")
    .antMatchers("/user/**").hasAnyAuthority("USER_READ");
  1. 方法级安全控制 (需开启 @EnableGlobalMethodSecurity):
复制代码
@PreAuthorize("hasRole('ADMIN')")
public void deleteUser() { ... }
  1. 自定义权限决策器 :实现 AccessDecisionManagerPermissionEvaluator

安全配置

Spring Security 默认拦截哪些请求?如何放行静态资源?

默认拦截所有请求(包括静态资源)。可通过 WebSecurityCustomizerHttpSecurity 放行:

复制代码
@Override
public void configure(WebSecurity web) {
    web.ignoring().antMatchers("/css/**", "/js/**", "/images/**");
}

如何实现自定义的认证入口和异常处理?

使用如下配置实现自定义处理器:

复制代码
http.exceptionHandling()
    .authenticationEntryPoint(myEntryPoint)      // 未认证处理
    .accessDeniedHandler(myAccessDeniedHandler); // 权限不足处理

什么是CSRF?Spring Security如何防护?

  • CSRF(跨站请求伪造) 是一种通过伪装用户请求盗用用户身份的攻击。

  • Spring Security 默认开启 CSRF 防护,需通过 <input type="hidden"> 或 header 传递 token。

  • 对于 REST API,可关闭 CSRF 防护:

复制代码
http.csrf().disable();

JWT 与无状态认证

Spring Security 如何集成 JWT?

  1. 登录成功生成 JWT Token 并返回给前端。

  2. 前端在请求头中携带 Token。

  3. 自定义 OncePerRequestFilter 验证 Token 并设置认证信息。

  4. 配置关闭 session 创建,改为无状态:

复制代码
http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);

Spring Security 与 OAuth2 有何关系?

Spring Security 是基础,OAuth2 是其扩展模块。Spring Security 提供 OAuth2 客户端、授权服务器、资源服务器支持。常用于:

  • 单点登录(SSO)

  • 社交登录(如 GitHub、Google)

  • 微服务资源授权


与 Spring Boot 的集成

Spring Boot 中如何使用 Spring Security?

只需引入依赖即可启用默认安全策略:

复制代码
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>
  • 默认账号:user

  • 默认密码:控制台输出

  • 所有请求都需认证

通过继承 WebSecurityConfigurerAdapterSecurityFilterChain 配置自定义规则。


Spring Security 的过滤器链顺序是怎样的?

Spring Security 使用 FilterChainProxy 管理一组安全过滤器,常见顺序如下:

  1. SecurityContextPersistenceFilter

  2. UsernamePasswordAuthenticationFilter

  3. BasicAuthenticationFilter

  4. ExceptionTranslationFilter

  5. FilterSecurityInterceptor

顺序非常重要,配置错误可能导致认证失败或安全漏洞。


如何在前后端分离项目中使用 Spring Security?

  1. 前端通过 Ajax 请求登录,后端返回 JWT 或 SessionID。

  2. 后端提供统一认证入口、异常响应、CORS 支持。

  3. 设置无状态认证方式,禁用 CSRF、Session。


高级特性

如何实现基于数据库的权限控制模型?

通过数据库定义用户-角色-权限表结构,查询权限信息填充到 GrantedAuthority,并在 UserDetailsService 中封装返回。


Spring Security 如何实现 Remember Me?

通过配置 rememberMe(),可在浏览器中持久化登录状态:

复制代码
http.rememberMe()
    .tokenValiditySeconds(7 * 24 * 3600)
    .key("secureKey")
    .userDetailsService(myUserDetailsService);
相关推荐
_dindong3 分钟前
Linux网络编程:Socket编程TCP
linux·服务器·网络·笔记·学习·tcp/ip
wanhengidc8 分钟前
服务器的安全性如何?
运维·服务器·安全·游戏·智能手机
卷卷的小趴菜学编程11 分钟前
Linux网络之----序列化和反序列化
网络·序列化·反序列化·守护进程·jsoncpp·进程组·前后台进程
曦樂~21 分钟前
【Qt】信号与槽(Signal and Slot)- 简易计算器
开发语言·数据库·qt
ZYMFZ39 分钟前
python面向对象
前端·数据库·python
滑水滑成滑头1 小时前
**发散创新:多智能体系统的探索与实践**随着人工智能技术的飞速发展,多智能体系统作为当今研究的热点领域,正受到越来越多关注
java·网络·人工智能·python
迎風吹頭髮1 小时前
Linux服务器编程实践55-网络信息API:gethostbyname与gethostbyaddr实现主机名解析
网络
newxtc2 小时前
【猿辅导-注册安全分析报告-无验证方式导致安全隐患】
开发语言·selenium·安全·yolo·安全爆破
风语者日志2 小时前
CTFSHOW—WEB4
网络·安全·web安全·网络安全·ctf
lang201509282 小时前
MySQL 8.0原子性DDL全面解析
数据库·mysql