spring-security(十)基本认证过程

本文介绍了Spring Security中认证的基本过程,包括从HTTP请求中获取用户名和密码、验证用户名密码的有效性、创建用户的安全上下文等步骤。通过一个示例程序展示了认证成功的条件及认证后的安全上下文状态。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言:
在spring security中认证具体指的是什么以及如何做的,本文做一个简单的阐述
环境
spring boot 版本:1.5.4.RELEASE

下面我们一起考虑一个简单的大家都熟悉的认证情景
[list]
[*]1.一个用户被提示输入用户名和密码
[*]2.系统验证用户名和密码是否合法
[*]3.用户的上下文信息被获取(如用户的权限列表)
[*]4.创建用户对应的安全上下文
[*]5.当用户继续执行后续操作时,系统的安全访问控制机制利用当前的安全上下文信息来判断这些操作是否被许可
[/list]

上面情景中的前三步就是基本的认证过程,下面让我们看下这在spring security中是如何发生的。
[list]
[*]1.从httpRequest中获取username和password,然后组合成一个实现了Authentication接口的UsernamePasswordAuthenticationToken实例
[*]2.组合成的token被传递给一个AuthenticationManager实例(ProviderManager)来验证
[*]3.验证成功AuthenticationManager会返回一个组装好的Authentication实例(包含用户的权限信息)
[*]4.通过调用SecurityContextHolder.getContext().setAuthentication(...)方法,并传入组装好的Authentication实例来创建安全上下文
[/list]
之后,当前用户就完成了认证。此过程,可以有如下代码来模拟

import org.springframework.security.authentication.*;
import org.springframework.security.core.*;
import org.springframework.security.core.authority.SimpleGrantedAuthority; import org.springframework.security.core.context.SecurityContextHolder;
public class AuthenticationExample {
private static AuthenticationManager am = new SampleAuthenticationManager();
public static void main(String[] args) throws Exception {
BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
while(true) {
System.out.println("Please enter your username:"); String name = in.readLine(); System.out.println("Please enter your password:"); String password = in.readLine();
try {
Authentication request = new UsernamePasswordAuthenticationToken(name, password); Authentication result = am.authenticate(request); SecurityContextHolder.getContext().setAuthentication(result);
break;
} catch(AuthenticationException e) { System.out.println("Authentication failed: " + e.getMessage());
}
}
System.out.println("Successfully authenticated. Security context contains: " +
SecurityContextHolder.getContext().getAuthentication());
}
}
class SampleAuthenticationManager implements AuthenticationManager {
static final List<GrantedAuthority> AUTHORITIES = new ArrayList<GrantedAuthority>();
static {
AUTHORITIES.add(new SimpleGrantedAuthority("ROLE_USER"));
}
public Authentication authenticate(Authentication auth) throws AuthenticationException { if (auth.getName().equals(auth.getCredentials())) {
return new UsernamePasswordAuthenticationToken(auth.getName(),
auth.getCredentials(), AUTHORITIES);
}
throw new BadCredentialsException("Bad Credentials"); }
}


其中SampleAuthenticationManager是我们实现的一个认证类,只是简单判断如果用户名和密码相同就认证成功,并赋给用户一个固定的USER权限。运行后程序的输出如下

Please enter your username:
bob
Please enter your password:
password
Authentication failed: Bad Credentials
Please enter your username:
bob
Please enter your password:
bob
Successfully authenticated. Security context contains: \
org.springframework.security.authentication.UsernamePasswordAuthenticationToken@441d0230: \
Principal: bob; Password: [PROTECTED]; \
Authenticated: true; Details: null; \
Granted Authorities: ROLE_USER

在实际应用中,我们也不会直接这样写代码,这里我们只是为了说明spring security的认证过程。这个例子也说明在spring security中如何判断认证成功,那就是SecurityContextHolder中包含一个完全组装好的Authentication对象。
这个例子也说明了spring security并不关心Authentication对象是如何存放到SecurityContextHolder中的,唯一需要确认的就是在AbstractSecurityInterceptor要鉴权一个用户时SecurityContextHolder中包含一个Authentication对象就OK了。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值