1. 概述
安全性是任何 Java 应用程序中不可或缺的一部分。市面上有很多安全框架可以帮我们处理认证、授权等安全问题。同时,在这些框架中,我们也会频繁遇到一些术语,比如 Subject(主体)、Principal(身份) 和 User(用户)。
本篇文章将为你梳理这些安全框架中的基本概念,解释它们之间的关系和区别,帮助你在设计和实现安全逻辑时更加得心应手。
2. Subject(主体)
在安全上下文中,Subject 代表请求的来源。简单来说,它是一个可以访问资源、获取信息或修改资源的实体。
✅ Subject 可以是:
- 一个用户
- 一个程序
- 一个进程
- 一个文件
- 一台计算机
- 一个数据库
...等等
举个例子:当一个人需要访问某个资源时,他必须先进行身份认证,以证明他是请求的合法来源。在这个场景下,这个人就是一个 Subject。
下面是一个基于 JAAS 的代码示例:
Subject subject = loginContext.getSubject();
PrivilegedAction privilegedAction = new ResourceAction();
Subject.doAsPrivileged(subject, privilegedAction, null);
这段代码的作用是:使用认证后的 Subject 执行一个特权操作。
3. Principal(身份)
认证成功后,Subject 会携带多个身份信息(Principal),比如角色、社保号、用户名等。这些身份信息就是 Principal。
举个例子:一个人可能拥有一个账户号 Principal(比如 “87654-3210”)和其他唯一标识符,用来把他和其他 Subject 区分开。
下面是一个登录成功后创建 UserPrincipal
并添加到 Subject 的示例:
@Override
public boolean commit() throws LoginException {
if (!loginSucceeded) {
return false;
}
userPrincipal = new UserPrincipal(username);
subject.getPrincipals().add(userPrincipal);
return true;
}
这段代码属于 JAAS 的 LoginModule,认证成功后会把用户身份添加到 Subject 中。
4. User(用户)
User 通常表示一个访问资源的人,可能是执行某个任务的终端用户,也可能是后台的操作员。
⚠️ 注意:User 本身也可以被当作一个 Principal 来使用。换句话说,Principal 是赋予 User 的身份标识。
在 JAAS 中,UserPrincipal
就是一个典型的例子:
UserPrincipal userPrincipal = new UserPrincipal("john_doe");
它代表的是一个具体的用户身份,绑定在 Subject 上。
5. Subject、Principal 和 User 的区别
这三者之间的关系可以用一句话总结:
User 是 Principal 的一种,而 Principal 是 Subject 的一部分。
更具体地说:
概念 | 含义 | 类型 |
---|---|---|
Subject | 请求来源的实体 | 最外层容器 |
Principal | 身份标识(角色、用户名等) | Subject 的属性 |
User | 代表一个具体用户 | Principal 的一种 |
✅ 举个通俗的例子:
- Subject:一台电脑
- Principal:用户名、角色、部门编号
- User:张三
6. 总结
本文讲解了安全框架中常见的三个核心概念:Subject、Principal 和 User,并通过代码示例展示了它们的使用方式和相互关系。
这些概念在 Spring Security、Shiro、JAAS 等框架中都有体现,掌握它们有助于你更深入地理解和设计系统安全机制。
所有示例代码均可在 GitHub 项目 中找到。