「工程实践」Spring Security(一)基础入门示例
Spring Security 是一个功能强大且高度可定制的身份验证和访问控制的安全框架。它是 Spring 应用程序在安全框架方面的公认标准。
其核心特性包括:认证和授权、常规攻击防范、与 Servlet 接口集成、与 Spring MVC 集成等。
常规攻击防范在 Spring Security 安全框架中是默认开启的,常见的威胁抵御方式有:防止伪造跨站请求(CSRF),安全响应头(HTTP Response headers),HTTP通讯安全等
1. 入门示例
新建 SpringBoot 项目,在 pom.xml 中增加 Spring Security 依赖:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
只要加入依赖,项目的所有接口都会被自动保护起来。
创建一个 Controller:
@RestController
public class HelloApi {
@GetMapping("/hello")
public String hello() {
return "hello";
}
}
导入spring-boot-starter-security启动后,Spring Security已经生效,默认拦截全部请求,如果用户没有登录,跳转到内置登录页面。
访问/hello接口 ,需要登录之后才能访问。

默认配置下,会自动生成一个 user 用户,并分配其随机密码,密码可以从控制台的日志信息中找到:

2. Spring Security默认配置项
Spring Boot 引入 Spring Security 启动后,将会自动开启如下配置项:
- 默认开启一系列基于
springSecurityFilterChain的Servlet过滤器,包含了几乎所有的安全功能,例如:保护系统URL、验证用户名、密码表单、重定向到登录界面等; - 创建
UserDetailsService实例,并生成随机密码,用于获取登录用户的信息详情; - 将安全过滤器应用到每一个请求上。
除此之外,Spring Security 还有一些其他可配置的功能:
- 限制所有访问必须首先通过认证;
- 生成默认登录表单;
- 创建用户名为
user的可以通过表单认证的用户,并为其初始化密码; - 使用
BCrypt方式加密密码; - 提供登出的能力;
- 保护系统不受
CSRF攻击; - 会话固定保护;
- 集成安全消息头;
- 提供一些默认的
Servlet接口,如:「getRemoteUser」、「getUserPrincipal」、「isUserInRole」、「login」和「logout」。
3. 配置文件定义用户信息
也可以直接在 application.yml 配置文件中配置用户的基本信息:
spring:
security:
user:
name: user
password: 123
配置完成后,重启项目,就可以使用这里配置的用户名/密码登录了。
4. Java代码定义用户信息
如果需要自定义逻辑时,只需要实现UserDetailsService接口即可。
@Service
public class UserDetailsServiceImpl implements UserDetailsService {
@Resource
private PasswordEncoder encoder;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
// 判断用户名是否存在(用户名也可查询数据库),如果不存在抛出UsernameNotFoundException
if(!username.equals("admin")){
throw new UsernameNotFoundException("用户名不存在");
}
// 把查询出来的密码进行解析,或直接把password放到构造方法中。
// 理解:password就是数据库中查询出来的密码,查询出来的内容不是123
String password = encoder.encode("123");
return new User(username,password, AuthorityUtils.commaSeparatedStringToAuthorityList("admin"));
}
}
返回值 UserDetails 是一个接口,要想返回 UserDetails 的实例就只能返回接口的实现类。
这里使用 Spring Security 中提供的 org.springframework.security.core.userdetails.User。
Spring Security 要求:当进行自定义登录逻辑时容器内必须有 PasswordEncoder 实例。
客户端密码和数据库密码是否匹配是由 Spring Security 去完成的,但 Security 中没有默认密码解析器。所以当自定义登录逻辑时要求必须给容器注入PaswordEncoder的bean对象。
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Bean
public PasswordEncoder getPasswordEncoder(){
/*
* BCryptPasswordEncoder是spring security官方推荐的解析器,
* 它是对bcrypt强散列方法的具体实现,基于Hash算法实现的单向加密。
* 可以通过strength控制加密强度,默认为10,长度越长安全性越高。
*/
return new BCryptPasswordEncoder();
}
}
重启项目后,在浏览器中输入账号:admin,密码:123,登录后就可以访问接口了。
相关系列文章
- 「工程实践」Spring Security(七)前后端分离权限控制-指令级权限
- 「工程实践」Spring Security(六)前后端分离菜单权限控制-前端动态路由
- 「工程实践」Spring Security(五)前后端分离后台菜单权限控制
- 「工程实践」Spring Security(四)基于Redis的Token自动续签优化
- 「工程实践」Spring Security(三)整合JWT实现无状态登录示例
- 「工程实践」Spring Security(二)安全架构与认证鉴权原理
- 「工程实践」Spring Security(一)基础入门示例
- 「工程实践」基于Shiro前后端分离的认证与授权(下.前端篇)
- 「工程实践」基于Shiro前后端分离的认证与授权(中.授权篇)
- 「工程实践」基于Shiro前后端分离的认证与授权(上.认证篇)
- 「学习笔记」安全认证 - Shiro安全框架入门
- 「学习笔记」安全认证 - JSON Web Token 入门
- 「学习笔记」安全认证 - MD5算法加盐实现用户密码加密