认识shiro

认证

身份认证:判断一个用户是否为一个合法用户的过程。

认证方式:用户名口令认证、短信验证码、第三方授权。

认证需要的关键对象:

  • Subject:主体,访问系统的用户,主体可以是用户、程序等
  • Principal:身份信息是主体进行身份认证的标识,标识必须具有唯一性,如用户名、手机号、邮箱地址。一个主题可以有多个身份,但必须有一个主身份(Primary Principal)
  • credential:凭证信息,只有主体自己知道的安全信息,如密码、证书

授权

授权:访问控制,控制谁能访问哪些资源。主体进行身份认证后,系统会为其分配对应的权限,当访问资源时,会校验其是否有此权限。

授权需要操作的对象:

  • 用户对象user:当前操作的用户、程序
  • 资源对象Resource:被访问的资源
  • 角色对象role:一组“权限操作许可权”的集合
  • 权限对象permission:权限操作许可权

什么是Shiro

Shiro是一个开源的安全认证框架。实现用户身份认证、权限授权、加密、会话管理等功能。

核心组件

subject

外部程序与subject进行交互,而Subject通过SecurityManager安全管理进行认证授权。

外部程序----------subject---------SecurityManager

SecurityManager(权限管理器)

它是Shiro的核心,对所有subject进行管理。通过SecurityManager完成subject的认证、授权。SecurityManager是通过Authenticator进行认证;通过Authorizer进行授权;通过SessionManager进行会话管理。SecurityManager是一个接口,继承Authenticator、Authorizer、SessionManager这三个接口。

Authenticator(认证器)

对用户登录进行身份认证

Authorizer(授权器)

认证通过后,在访问功能时通过Authorizer判断用户是否有操作权限

Realm(数据库读取+认证功能+授权功能实现)

Realm相当于DataSource数据源。SecurityManager进行安全认证需要通过Realm获取用户权限数据。

比如:用户身份数据在数据库,那么realm需要从数据库获取身份信息。

注意:realm除了从数据源获取身份信息,在realm中还有认证授权校验的相关代码。

SessionManager(会话管理)

Shiro框架定义的一套会话管理系统,它不依赖Web容器的Session,所以Shiro可以用在非Web应用上,也可以将分布式应用的会话集中在一点管理,此特性可使它实现单点登录。

SessionDAO(会话DAO)

可通过jdbc将会话存储到数据库,也可以把 Session存储到缓存服务器。

CacheManager(缓存管理)

将用户权限数据存储在缓存,可以提高性能。

Cryptography(密码管理)

Shiro提供的一套加密/解密组件,比如提供常用的散列、加/解密功能。

Shiro入门

身份认证

认证流程:

  1. Shiro把用户的数据封装成标识token,token封装了用户名、密码等信息
  2. subject获取到这个标识token
  3. subject把标识token交给SecurityManager,在SecurityManager安全中心中,SecurityManager把标识token交给认证器Authenticator进行身份认证。
  4. 认证器Authenticator将标识token与数据源Realm对比,验证token是否合法。

代码示例

导入依赖

<dependency>
    <groupId>org.apache.shiro</groupId>
    <artifactId>shiro-core</artifactId>
    <version>1.3.2</version>
</dependency>
<!-- 这里有用到日志打印,所以引入 -->
<dependency>
    <groupId>org.slf4j</groupId>
    <artifactId>slf4j-log4j12</artifactId>
    <version>1.6.1</version>
</dependency>
    <dependency>
        <groupId>org.apache.logging.log4j</groupId>
        <artifactId>log4j-core</artifactId>
        <version>2.14.1</version>
    </dependency>
    <dependency>
        <groupId>org.apache.logging.log4j</groupId>
        <artifactId>log4j-api</artifactId>
        <version>2.14.1</version>
    </dependency>

构造shiro.ini文件

# -----------------------------------------------------------------------------
# users用来定义用户
[users]
# 用户名 = 密码,角色1,角色2...
admin = secret, admin
guest = guest, guest
aa = 123456, guest
# -----------------------------------------------------------------------------
# roles用来定义角色
[roles]
# 角色 = 权限 (* 代表所有权限)
admin = *
# 角色 = 权限 (* 代表所有权限)
guest = see
aa = see

示例代码

package demo;

import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.config.IniSecurityManagerFactory;
import org.apache.shiro.subject.Subject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class ShiroDemo {
    private static final Logger log = LoggerFactory.getLogger(ShiroDemo.class);
    public static void main(String[] args) {
        //1.导入权限ini文件,创建SecurityManagerFactory
        IniSecurityManagerFactory factory = new IniSecurityManagerFactory("classpath:shiro.ini");
        //2.获取SecurityManager,绑定到SecurityUtils中
        SecurityManager securityManager =factory.getInstance();
        SecurityUtils.setSecurityManager( securityManager);
        //3.获取一个用户主体
        Subject currentUser = SecurityUtils.getSubject();
        UsernamePasswordToken token = new UsernamePasswordToken("guest", "guest");
        currentUser.login(token);
        System.out.println("是否登录成功:"+currentUser.isAuthenticated());
    }
}

运行结果

8P0M)%PYDWKZA7IA(TM0J

posted @ 2026-01-07 21:04  NE_STOP  阅读(162)  评论(0)    收藏  举报