1. 程式人生 > >Shiro進行認證授權

Shiro進行認證授權

AuthenticatingRealm類是用來獲取資料的類,是一個抽象類,預設獲取配置檔案中的資料的子類為SimpleAccountRealm,想要獲取資料庫中的資料需要自己定義一個實現類extends AuthenticatingRealm,該類中只有認證方式。想要即有認證方法,也存在授權方法,需要去繼承 AuthorizingRealm 類,該類實現了 AuthenticatingRealm,也是一個抽象類,所以存在兩個抽象方法(認證、授權)需要去實現。

AuthonticatingRealm抽象類中存在一個抽象方法doGetAuthenticationInfo用該方法獲取資料
實現方式:

  • 預設實現SimpleAccountRealm,獲取配置檔案中的使用者資料
  • 自定義實現:獲取資料庫中的資料

SimpleAccountRealm:本身不做資料比對,只獲取資料
AuthonticatingRealm存在一個進行資料比對的屬性:CredentialsMatcher是一個介面,該介面的實現類SimpleCredentialsMatch通過equals方法進行資料比對,由於使用者輸入的密碼,和資料庫中通過加鹽加密雜湊的密碼一定不會相同,所以不能用equals方法進行比對,需要將預設的比對器轉換為HashedCredentialsMatcher比對器

Shiro預設執行SimpleAccountRealm獲取配置檔案資料,想要獲取資料庫中的資料步驟:

  • 開發自定義realm extends AuthonticatingRealm
  • 告知shiro使用自定義Realm
  • Shiro整合資料庫時需要匯入commons-logging包

注意:新增快取時,需要匯入encache自身的依賴

<dependency>
            <groupId>org.ehcache</groupId>
            <artifactId>ehcache</artifactId>
            <version>3.6.3</version>
        </dependency>

Shiro過濾器

@Configuration
public class ShiroFilterConf {
    @Bean//Shiro過濾器  判斷請求是否認證成功                  該方法由工廠呼叫,該形參存在在工廠中,所以可直接注入型別即可
    public ShiroFilterFactoryBean getShiroFilterFactoryBean(SecurityManager securityManager) {
        ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
        shiroFilterFactoryBean.setSecurityManager(securityManager);
        //過濾器攔截請求  預設不攔截,所以需要進行相關攔截配置
        Map<String, String> map = new HashMap<String, String>();

        map.put("/main/main.jsp", "authc");//新增認證過濾器 攔截所有的請求  沒有認證則跳轉到登入介面
        map.put("/**", "anon");
        shiroFilterFactoryBean.setSuccessUrl("/main/main.jsp");
        shiroFilterFactoryBean.setFilterChainDefinitionMap(map);//定義過濾器鏈(多個過濾器)
        return shiroFilterFactoryBean;
    }

    @Bean
    public SecurityManager getSecurityManager(Realm myRealm, CacheManager cacheManager) {
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setCacheManager(cacheManager);
        securityManager.setRealm(myRealm);
        return securityManager;
    }

    @Bean
    public Realm getRealm(CredentialsMatcher hashedCredentialsMatcher) {
        MyRealm myRealm = new MyRealm();
        myRealm.setCredentialsMatcher(hashedCredentialsMatcher);
        return myRealm;
    }

    @Bean
    public CredentialsMatcher getCredentialsMatcher() {
        HashedCredentialsMatcher hashedCredentialsMatcher = new HashedCredentialsMatcher();
        hashedCredentialsMatcher.setHashAlgorithmName("md5");
        hashedCredentialsMatcher.setHashIterations(1024);
        return hashedCredentialsMatcher;
    }

    @Bean  
    public CacheManager getCacheManager() {
        EhCacheManager ehCacheManager = new EhCacheManager();
        return ehCacheManager;
    }

}

自定義Realm

public class MyRealm extends AuthorizingRealm {
    @Autowired
    AdminMapper adminMapper;
    @Autowired
    RoleMapper roleMapper;
     @Override //授權
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        String primaryPrincipal = (String) principalCollection.getPrimaryPrincipal();//獲得使用者名稱
        //通過該使用者名稱查詢該使用者的角色
        List<Role> roleList = roleMapper.queryAllRoleByName(primaryPrincipal);

        AuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();//授權資訊  新增許可權
        //通過角色獲取到許可權,將許可權新增至授權資訊中
        if (!roleList.isEmpty()) {
            for (Role role : roleList) {
                List<Authority> authorities = roleMapper.queryAllAuthorityByRole(role.getName());
                ((SimpleAuthorizationInfo) authorizationInfo).addRole(role.getName());
                if (!authorities.isEmpty()) {
                    for (Authority authority : authorities) {
                        //將許可權新增到授權資訊中
                        ((SimpleAuthorizationInfo) authorizationInfo).addStringPermission(authority.getAuthority());
                    }
                }

            }
        }

        return authorizationInfo;
    }

    @Override //認證
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        String username = (String) authenticationToken.getPrincipal();//獲取身份資訊
        Admin admin = new Admin();
        admin.setName(username);
        Admin admin1 = adminMapper.selectOne(admin);
        AuthenticationInfo authenticationInfo = null;
        if (admin1 != null) {//認證器
            authenticationInfo = new SimpleAuthenticationInfo(admin1.getName(), admin1.getPassword(), ByteSource.Util.bytes(admin1.getSalt()), this.getName());
        }
        return authenticationInfo;
    }
}