• 005 自定义Realm


    一 . 概述

      上几节我们一直再使用int文件充当realm,现在这一届我们就使用自定义的Realm完成认证和授权操作.

      在前面我们分析到我们的自定义的Realm需要继承AuthorizingRealm这个类.


    二 . 编写自定义Realm 

    public class CustomRealm extends AuthorizingRealm{
        @Override
        protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
            return null;
        }
        
        @Override
        protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
            return null;
        }
    
    }

    我们首先定义一个类继承了AuthorizingRealm这个类,其中需要我们实现的是两个方法.

     protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException

    认证方法 : 通过用户传入的tokean对象进行认证操作,认证成功就返回用户的身份信息.认证失败就抛出异常.

     protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {

    授权方法:通过传入的身份信息,获取用户具有的权限信息(角色和权限).


    三 .实现Realm

    public class CustomRealm extends AuthorizingRealm{
        //认证方法
        @Override
        protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken info) throws AuthenticationException {
            //获取账号和密码
            UsernamePasswordToken token = (UsernamePasswordToken) info;
            String username = token.getUsername();
            String password = new String(token.getPassword());
            //这里模拟一下认证
            if(!"trek".equals(username)) {
                throw new UnknownAccountException("账号不存在!");
            }
            if(!"123".equals(password)) {
                throw new IncorrectCredentialsException("密码不正确!!");
            }
            //此处说明认证是成功的了.
            //现在要返回用户的身份信息了
            SimpleAccount account = new SimpleAccount(username,password,getName());
            return account;
        }
        
        //授权的方法
        @Override
        protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
            //获取身份信息,这里的参数就是上面方法的返回值
            String  uaername = (String) principals.getPrimaryPrincipal();
            //--通过身份信息查询用户的角色和权限信息
            Set<String> roles = new HashSet<String>();
            roles.add("admin");
            Set<String> pers = new HashSet<String>();
            pers.add("user:add");
            //返回授权信息
            SimpleAuthorizationInfo info  =new  SimpleAuthorizationInfo();
            info.addRoles(roles);
            info.addStringPermissions(pers);
            return info;
        }
    
    }

    我们实现了自定的Realm.


    四 .配置Realm

    [main]
    realm=com.trek.shiro.base.CustomRealm
    securityManager.realm=$realm

    将我们的ini文件变成如上的内容,现在我们的账号和密码信息都是从我们的自定义Realm之中获取的.

    上面的代码相当于Spring的IOC的配置方式,比较容易理解.

    测试代码:

    //实现shiro的认证过程
            //创建SecurityManager
            SecurityManager securityManager = new IniSecurityManagerFactory("classpath:shiro.ini").createInstance();
            //将当前的SecurityManager设置到当前的环境之中
            SecurityUtils.setSecurityManager(securityManager);
            
            //下面实现的是一个登陆的功能
            //获取Subkect,相当与一个Currentuser
            Subject currentUser = SecurityUtils.getSubject();
            
            //创建认证需要的token
            UsernamePasswordToken token = new UsernamePasswordToken("trek","123");
            
            //实现登录功能
            try {
                currentUser.login(token);
            } catch (AuthenticationException e) {
                logger.info("认证失败,账号为{},密码为{}",token.getUsername(),new String(token.getPassword()));
                throw new AuthenticationException();
            }
            
            logger.info("认证成功!!");
            
            //此处完成shiro的授权操作
            
            //角色授权
            logger.info("当前的用户是否具有admin的角色{}",currentUser.hasRole("admin"));
            
            //权限授权
            logger.info("当前的用户是否具有user:add的权限{}",currentUser.isPermitted("user:add"));

    上述的测试代码和我们之前的代码没有变过,改变的只是我们的Realm的实现.


    五 .总结Realm的定制

    自定义Realm比较简单,流程都是一致的,只是我们的账号,密码,角色,权限信息的获取方式不一样了.

  • 相关阅读:
    C# Winform 使用Quartz
    C# datagridview显示行号
    C#时间格式问题解决,不受系统时间格式影响
    PLSQL永久激活
    C#内存回收
    Modbus的通信参数存在flash中,如果改乱了,该怎么办--FreeModbus从站设计(12)
    如何把Modbus的通信参数存在单片机的flash中--FreeModbus从站设计(11)
    为什么有的PLC需要上电停止功能,能防止PLC变砖(可编程控制器 串口通信)
    让串口和Modbus初始化的参数同步起来-STM32F103、FreeModbus从站设计(6)
    STM32F103、FreeModbus从站设计(5)-如何将FreeModbus代码加入keil工程
  • 原文地址:https://www.cnblogs.com/trekxu/p/9048798.html
Copyright © 2020-2023  润新知