背景:药品在线招投标系统 - 后端服务
作为学校课程设计,该系统虽简洁但聚焦于核心功能实现,重点将围绕 Spring Boot Security Security 的关键知识点展开解析。项目源码可参考:Gitee 仓库
项目简介
基于 Spring Boot 3.3.4 开发的药品在线招投标系统后端服务,提供标准化 RESTful API 接口,支撑前端完成招投标全流程交互。
技术栈
- 框架:Spring Boot 3.3.4
- Java 版本:JDK 17
- 数据库:MySQL
- ORM:Spring Data JPA
- 安全框架:Spring Security + JWT
- 构建工具:Maven
跨域配置(CorsConfig)
前后端分离架构中,跨域请求是常见场景。以下是项目中基于 Spring 的跨域解决方案:
package com.ecut.drug_bid.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import org.springframework.web.filter.CorsFilter;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class CorsConfig implements WebMvcConfigurer {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**") // 对所有接口生效
.allowedOriginPatterns("*") // 允许所有来源(生产环境需指定具体域名)
.allowedMethods("GET", "POST", "PUT", "DELETE", "PATCH", "OPTIONS") // 允许的HTTP方法
.allowedHeaders("*") // 允许所有请求头
.allowCredentials(false) // 不允许携带凭证(与通配符来源兼容)
.maxAge(3600); // 预检请求缓存时间(1小时)
}
@Bean
public CorsFilter corsFilter() {
CorsConfiguration config = new CorsConfiguration();
config.addAllowedOriginPattern("*");
config.addAllowedHeader("*");
config.addAllowedMethod("*");
config.setAllowCredentials(false);
config.setMaxAge(3600L);
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
source.registerCorsConfiguration("/**", config);
return new CorsFilter(source);
}
}
跨域配置解析
-
为何需要跨域配置? 浏览器的同源策略规定:只有协议、域名、端口完全一致的请求才被视为 “同源”,否则会被拦截。前后端分离架构中,前端(如
http://localhost:8080)与后端(如http://localhost:8081)通常不同源,因此需通过 CORS 配置告知浏览器 “允许该前端访问后端接口”。 -
两种跨域配置方式项目同时使用两种配置,确保规则在不同场景下生效:
- WebMvcConfigurer 接口:通过重写
addCorsMappings方法定义跨域规则,适用于常规请求。 - CorsFilter 过滤器:优先级高于前者,会在请求进入控制器前拦截验证,尤其适合与 Spring Security 配合(确保跨域规则在安全过滤前生效)。
两者配置内容一致,双重配置是为兼容不同 Spring 版本或复杂场景。
- WebMvcConfigurer 接口:通过重写
CSRF(跨站请求伪造)
一种网络攻击方式:攻击者诱导已登录目标网站的用户,在不知情的情况下以其身份执行非本意操作(如转账、修改信息)。
攻击原理
- 用户登录网站 A 后,浏览器保留其认证信息(如 Cookie);
- 攻击者诱导用户访问恶意网站 B,B 构造针对 A 的请求,利用用户的认证信息向 A 发送请求;
- 网站 A 因请求携带合法认证信息,误认为是用户操作而执行请求。
防御措施
- 生成 CSRF Token 并验证请求令牌;
- 检查请求的 Referer/Origin 头,确认来源可信;
- 设置 SameSite Cookie 属性,阻止跨域请求携带 Cookie;
- 敏感操作要求二次验证(如验证码)。
SecurityConfig 核心配置
SecurityConfig是 Spring Security 的核心配置类,用于定义应用安全策略:
- 通过
@EnableWebSecurity启用 Web 安全功能; - 配置
SecurityFilterChain定义安全过滤器链; - 依赖
@RequiredArgsConstructor注入JwtAuthenticationFilter(Lombok 自动生成构造函数)。
为何禁用 CSRF?
项目作为前后端分离架构,采用 JWT 认证而非传统 Session,因此可安全禁用 CSRF:
- JWT 存储方式:JWT 通常放在 HTTP 请求头的
Authorization字段中,而非 Cookie,浏览器不会自动附加到跨站请求; - CSRF 攻击依赖:传统 CSRF 依赖浏览器自动发送 Cookie 的机制,而 JWT 不依赖此特性;
- 无状态设计:通过
sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS)设置无状态会话,进一步切断 CSRF 攻击链条。
安全保障措施
- 自定义
JwtAuthenticationFilter验证令牌合法性; - 采用无状态会话管理,避免会话劫持风险;
- 细化权限控制,确保 API 访问符合角色权限规则。