Springboot整合Shiro

一、導入依賴

<!--shiro-->
<dependency>
    <groupId>org.apache.shiro</groupId>
    <artifactId>shiro-spring</artifactId>
    <version>1.4.0</version>
</dependency>

二、建立ShiroRealm.java文件

(這裏按照需求,只作登陸認證這塊)java

package com.hyqfx.manager.shiro;

import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.hyqfx.manager.entity.po.SystemAdmin;
import com.hyqfx.manager.service.ISystemAdminService;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;

public class ShiroRealm extends AuthorizingRealm {

    @Autowired
    private ISystemAdminService adminService;

    //受權
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        /*
        //獲取登陸用戶名
        String name= (String) principalCollection.getPrimaryPrincipal();
        //查詢用戶名稱
        User user = loginService.findByName(name);
        //添加角色和權限
        SimpleAuthorizationInfo simpleAuthorizationInfo = new SimpleAuthorizationInfo();
        for (Role role:user.getRoles()) {
            //添加角色
            simpleAuthorizationInfo.addRole(role.getRoleName());
            for (Permission permission:role.getPermissions()) {
                //添加權限
                simpleAuthorizationInfo.addStringPermission(permission.getPermission());
            }
        }
        return simpleAuthorizationInfo;*/


        return null;
    }

    //認證
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        //加這一步的目的是在Post請求的時候會先進認證,而後在到請求
        if (authenticationToken.getPrincipal() == null) {
            return null;
        }
        //獲取用戶信息
        String name = authenticationToken.getPrincipal().toString(); 
        SystemAdmin admin = adminService.selectOne(new EntityWrapper<SystemAdmin>().eq("username",name));

        if (admin == null) {
            return null;
        } else {
            //這裏驗證authenticationToken和simpleAuthenticationInfo的信息
            SimpleAuthenticationInfo simpleAuthenticationInfo = new SimpleAuthenticationInfo(name, admin.getPassword().toString(), getName());
            return simpleAuthenticationInfo;
        }
    }

}

三、建立ShiroConfiguration.java文件

package com.becl.config;

import com.becl.shiro.PasswordMatcher;
import com.becl.shiro.ShiroRealm;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.HashMap;
import java.util.Map;

@Configuration
public class ShiroConfiguration {



    //將本身的驗證方式加入容器
    @Bean
    public ShiroRealm myShiroRealm() {
        ShiroRealm myShiroRealm = new ShiroRealm();
        myShiroRealm.setCredentialsMatcher(passwordMatcher());//裝配自定義的密碼驗證方式
        return myShiroRealm;
    }

    // 配置加密方式
    // 配置了一下,這貨就是驗證不過,,改爲手動驗證算了,之後換加密方式也方便
    @Bean
    public PasswordMatcher passwordMatcher() {
        return new PasswordMatcher();
    }

    //權限管理,配置主要是Realm的管理認證
    @Bean
    public SecurityManager securityManager() {
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(myShiroRealm());
        return securityManager;
    }

    //Filter工廠,設置對應的過濾條件和跳轉條件
    @Bean
    public ShiroFilterFactoryBean shiroFilterFactoryBean(SecurityManager securityManager) {
        ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
        shiroFilterFactoryBean.setSecurityManager(securityManager);
        Map<String,String> map = new HashMap<String, String>();
        //登出
        map.put("/logout","logout");
        //不須要認證
        map.put("/logout","anon");
        map.put("/login*","anon");
        map.put("/shiroError","anon");
        //對全部用戶認證
        map.put("/**","authc");
        //map.put("/**","anon");
        //登陸
        shiroFilterFactoryBean.setLoginUrl("/login");
        //首頁
        shiroFilterFactoryBean.setSuccessUrl("/index");
        //錯誤頁面,認證不經過跳轉
        shiroFilterFactoryBean.setUnauthorizedUrl("/shiroError");
        shiroFilterFactoryBean.setFilterChainDefinitionMap(map);
        return shiroFilterFactoryBean;
    }

    //加入註解的使用,不加入這個註解不生效
    @Bean
    public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor(SecurityManager securityManager) {
        AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor = new AuthorizationAttributeSourceAdvisor();
        authorizationAttributeSourceAdvisor.setSecurityManager(securityManager);
        return authorizationAttributeSourceAdvisor;
    }

}

四、自定義Shiro的密碼比較器

package com.becl.shiro;

import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.authc.credential.SimpleCredentialsMatcher;
import org.mindrot.jbcrypt.BCrypt;

/**
 * 自定義密碼比較器
 */
public class PasswordMatcher extends SimpleCredentialsMatcher {


    @Override
    public boolean doCredentialsMatch(AuthenticationToken token, AuthenticationInfo info) {
        UsernamePasswordToken utoken=(UsernamePasswordToken) token;

        //得到用戶輸入的密碼:(能夠採用加鹽(salt)的方式去檢驗)
        String inPassword = new String(utoken.getPassword());
        String username = utoken.getUsername();

        //得到數據庫中的密碼
        String dbPassword = (String) info.getCredentials();


        //進行密碼的比對
        boolean flag = BCrypt.checkpw(inPassword,dbPassword);
        return flag;
    }

}
相關文章
相關標籤/搜索