Springbooot集成Shiro简单使用

1.Shiro架构

Shiro三个主要的概念:

  1. Subject
  2. SecurityManager
  3. Realms

在这里插入图片描述

Shiro外部架构

  • Subject:主体,当前参与应用安全部分的主体。可以是用户,可以是第三方服务,可以是cron 任务,或者任何东西。主要指一个正在与当前软件交互的东西。所有Subject都需要SecurityManager,当与Subject进行交互,这些交互行为实际上被转换为与SecurityManager的交互
  • SecurityManager:安全管理员,Shiro架构的核心,它就像Shiro内部所有原件的保护伞。然而一旦配置了SecurityManager,SecurityManager就用到的比较少,开发者大部分时间都花在Subject上面。当你与Subject进行交互的时候,实际上是SecurityManager在背后帮你举起Subject来做一些安全操作。
  • Realms:Realms作为Shiro和应用的连接桥,当需要与安全数据交互的时候,像用户账户,或者访问控制,Shiro就从一个或多个Realms中查找。Shiro提供了一些可以直接使用的Realms,如果默认的Realms不能满足你的需求,你也可以定制自己的Realms

Shiro整体架构

  1. Authenticator:认证器,管理登陆与登出。

  2. Authorizer:授权器,赋予主体权限。

  3. Session Manager:session管理器,session管理机制。不借助任何web容器使用session

  4. Session Dao:session操作,主要增删改查。

  5. Cache Manager:缓存管理器

  6. Pluggable Realms(1 or more):shiro与数据库的连接,认证授权校验

  7. Cryptography:数据加密

Shiro核心组件

  • Subject 即主体,外部引用于 Subject 进行交互,Subject 记录了当前操作用户,将用户的概念理解为当前操作的主体,可能是一个通过浏览器请求的用户,也可能是一个运行的程序。Subject 在 Shrio 中是一个接口,接口中定义了很多认证授权相关的方法,外部程序通过 Sbject 进行认证授权,而 Sbject 是通过 SecurityManager 安全管理器进行认证授权的。

  • SecurityManager 即安全管理器,对全部的 Sbject 进行安全管理,它是 Shrio 的核心,通过 SecurityManager 可以完成全部 Sbject 的认证、授权等。实质上 SecurityManager 是通过 Authenticator 进行认证,通过 Authorizer 进行授权,通过 SessionManager 进行会话管理等。SecurityManager是一个接口,继承了 Authenticator ,Authorizer ,SessionManager 这三个接口。

  • Authenticator即认证器,对用户身份进行认证,Authenticator 是一个接口,Shrio 提供了 ModularRealmAuthenticator实现类,通过ModularRealmAuthenticator 基本上可以满足大多数需求,也可以自定义认证器。
    Authorizer即授权器,用户通过认证器认证通过,在访问功能时需要通过授权器判断用户是否有此功能的操作权限。

  • Realm即领域,相当于 datasource 数据源,SecurityManager 进行安全认证需要通过 Realm 获取用户权限数据,比如:如果用户身份数据在数据库,那么 Realm 就需要从数据库获取用户身份信息。不要把 Realm 理解成只是从数据源取数据,在 Realm 中还有认证授权校验的相关代码。

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

  • SessionDAO 即会话DAO,是对 Session 会话操作的一套接口,比如要将 Session 存储到数据库,可以通过 jdbc 将会话存储到数据库。

  • CacheManager 即缓存管理,将用户权限数据存储在缓存,这样可以提高性能。

  • Cryptografy即密码管理,Shrio 提供了一套解密/加密的组件,方便开发。比如提供常用的散列、加/解密功能。

2.Shiro环境搭建

主要分三步

  1. 创建realm领域对象
  2. 创建DefaultWebSecurityManager安全管理器
  3. 创建ShiroFilterFactoryBean 设置安全管理器

1.导入maven

   <!-- https://mvnrepository.com/artifact/org.apache.shiro/shiro-spring -->
        <dependency>
            <groupId>org.apache.shiro</groupId>
            <artifactId>shiro-spring</artifactId>
            <version>1.6.0</version>
        </dependency>

2.编写Realm

public class UserRealm extends AuthorizingRealm {
    //授权
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        return null;
    }
    //认证
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        return null;
    }
}

3.编写ShiroConfig

@Configuration
public class ShiroConfig {
    //ShiroFilterFactoryBean 3
    @Bean
    public ShiroFilterFactoryBean getShiroFilterFactoryBean(@Qualifier("getDefaultWebSecurityManager") DefaultWebSecurityManager defaultWebSecurityManager){
        ShiroFilterFactoryBean bean = new ShiroFilterFactoryBean();
        //设置安全管理器
        bean.setSecurityManager(defaultWebSecurityManager);
        return bean;

    }
    //DefaultWebSecurityManager 2
    @Bean
    public DefaultWebSecurityManager getDefaultWebSecurityManager(@Qualifier("userRealm") UserRealm userRealm){
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(userRealm);
        return securityManager;

    }
    //创建realm对象 1
    @Bean(name = "userRealm")
    public UserRealm userRealm(){
        return new UserRealm();
    }
}

3.Shiro用户登录拦截与认证

shiro的内置过滤器各个权限

  • anno:无需认证就可以访问
  • authc:必须认证了才能访问
  • user:必须拥有记住我功能才能访问
  • perms:必须拥有对某个资源的权限才能访问
  • role:拥有某个角色权限才能访问

在getShiroFilterFactoryBean中添加内置过滤器实现登录拦截
bean.setLoginUrl("/user/toLogin"); 可以设置拦截时的重定向

    @Bean
    public ShiroFilterFactoryBean getShiroFilterFactoryBean(@Qualifier("getDefaultWebSecurityManager") DefaultWebSecurityManager defaultWebSecurityManager){
        ShiroFilterFactoryBean bean = new ShiroFilterFactoryBean();
        //设置安全管理器
        bean.setSecurityManager(defaultWebSecurityManager);
        //添加shiro的内置过滤器
        /*
            anno:无需认证就可以访问
            authc:必须认证了才能访问
            user:必须拥有记住我功能才能访问
            perms:必须拥有对某个资源的权限才能访问
            role:拥有某个角色权限才能访问
         */
        Map<String, String> filterMap = new LinkedHashMap<>();
        //设置添加和修改页面必须认证了才能访问
         filterMap.put("/users/add","authc");
        filterMap.put("/users/update","authc");


        bean.setFilterChainDefinitionMap(filterMap);

        //设置如果没有权限就跳转到登录页面
        bean.setLoginUrl("/user/toLogin");
        return bean;

    }

在UserRealm 下的 doGetAuthenticationInfo方法中 添加用户执行认证

  @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        System.out.println("执行了认证");
        String username = "root";
        String password = "123456";
        UsernamePasswordToken userToken = (UsernamePasswordToken) authenticationToken;
        if (!userToken.getUsername().equals(username)){
            return null; //抛出异常,UnknownAccountException

        }
        //密码认证,shiro自己做

        return new SimpleAuthenticationInfo("",password,"");
    }

在controller中获取用户,封装用户登录的数据和登录认证

    @PostMapping("/login")
    public String login(String username, String password, Model model){
        //获取当前的用户
        Subject subject = SecurityUtils.getSubject();
        //封装用户的登录数据
        UsernamePasswordToken token = new UsernamePasswordToken(username,password);
        //执行登录方法,如果说没有异常就说明登录成功
        try {
            //登陆成功返回首页
            subject.login(token);
            return "index";
        }catch (UnknownAccountException e){
            //用户名错误返回登录页
            model.addAttribute("msg","用户名错误");
            return "login";
        }catch (IncorrectCredentialsException e){
            //密码错误返回登录页
            model.addAttribute("msg","密码错误");
            return "login";
        }

    }
  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值