溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

怎么在shiro使用ssm框架

發(fā)布時(shí)間:2021-04-21 15:47:19 來(lái)源:億速云 閱讀:177 作者:Leah 欄目:開(kāi)發(fā)技術(shù)

本篇文章為大家展示了怎么在shiro使用ssm框架,內(nèi)容簡(jiǎn)明扼要并且容易理解,絕對(duì)能使你眼前一亮,通過(guò)這篇文章的詳細(xì)介紹希望你能有所收獲。

1.在pom.xml中引入依賴

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

    <!-- https://mvnrepository.com/artifact/org.apache.shiro/shiro-web -->
    <dependency>
      <groupId>org.apache.shiro</groupId>
      <artifactId>shiro-web</artifactId>
      <version>1.6.0</version>
    </dependency>
    <!-- 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>

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

2.新建并配置緩存ehcache.xml

怎么在shiro使用ssm框架

<ehcache>

    <!-- Sets the path to the directory where cache .data files are created.

         If the path is a Java System Property it is replaced by
         its value in the running VM.

         The following properties are translated:
         user.home - User's home directory
         user.dir - User's current working directory
         java.io.tmpdir - Default temp file path -->
    <diskStore path="java.io.tmpdir"/>
    
    <cache name="authorizationCache"
           eternal="false"
           timeToIdleSeconds="3600"
           timeToLiveSeconds="0"
           overflowToDisk="false"
           statistics="true">
    </cache>

    <cache name="authenticationCache"
           eternal="false"
           timeToIdleSeconds="3600"
           timeToLiveSeconds="0"
           overflowToDisk="false"
           statistics="true">
    </cache>

    <cache name="shiro-activeSessionCache"
           eternal="false"
           timeToIdleSeconds="3600"
           timeToLiveSeconds="0"
           overflowToDisk="false"
           statistics="true">
    </cache>

    <!--Default Cache configuration. These will applied to caches programmatically created through
        the CacheManager.

        The following attributes are required for defaultCache:

        maxInMemory       - Sets the maximum number of objects that will be created in memory
        eternal           - Sets whether elements are eternal. If eternal,  timeouts are ignored and the element
                            is never expired.
        timeToIdleSeconds - Sets the time to idle for an element before it expires. Is only used
                            if the element is not eternal. Idle time is now - last accessed time
        timeToLiveSeconds - Sets the time to live for an element before it expires. Is only used
                            if the element is not eternal. TTL is now - creation time
        overflowToDisk    - Sets whether elements can overflow to disk when the in-memory cache
                            has reached the maxInMemory limit.

        -->
    <defaultCache
        maxElementsInMemory="10000"
        eternal="false"
        timeToIdleSeconds="120"
        timeToLiveSeconds="120"
        overflowToDisk="true"
        />

    <!--Predefined caches.  Add your cache configuration settings here.
        If you do not have a configuration for your cache a WARNING will be issued when the
        CacheManager starts

        The following attributes are required for defaultCache:

        name              - Sets the name of the cache. This is used to identify the cache. It must be unique.
        maxInMemory       - Sets the maximum number of objects that will be created in memory
        eternal           - Sets whether elements are eternal. If eternal,  timeouts are ignored and the element
                            is never expired.
        timeToIdleSeconds - Sets the time to idle for an element before it expires. Is only used
                            if the element is not eternal. Idle time is now - last accessed time
        timeToLiveSeconds - Sets the time to live for an element before it expires. Is only used
                            if the element is not eternal. TTL is now - creation time
        overflowToDisk    - Sets whether elements can overflow to disk when the in-memory cache
                            has reached the maxInMemory limit.

        -->

    <!-- Sample cache named sampleCache1
        This cache contains a maximum in memory of 10000 elements, and will expire
        an element if it is idle for more than 5 minutes and lives for more than
        10 minutes.

        If there are more than 10000 elements it will overflow to the
        disk cache, which in this configuration will go to wherever java.io.tmp is
        defined on your system. On a standard Linux system this will be /tmp"
        -->
    <cache name="sampleCache1"
        maxElementsInMemory="10000"
        eternal="false"
        timeToIdleSeconds="300"
        timeToLiveSeconds="600"
        overflowToDisk="true"
        />

    <!-- Sample cache named sampleCache2
        This cache contains 1000 elements. Elements will always be held in memory.
        They are not expired. -->
    <cache name="sampleCache2"
        maxElementsInMemory="1000"
        eternal="true"
        timeToIdleSeconds="0"
        timeToLiveSeconds="0"
        overflowToDisk="false"
        />

    <!-- Place configuration for your caches following -->

</ehcache>

3.在spring配置文件applicationContext.xml配置shiro

怎么在shiro使用ssm框架

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
    <!-- spring 配置文件  主要配置和業(yè)務(wù)邏輯有關(guān)的 -->
    <context:property-placeholder location="classpath:dbconfig.properties"/>
    <!-- 數(shù)據(jù)源 -->
    <bean id="pooledDataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
        <property name="jdbcUrl" value="${jdbc.jdbcUrl}"></property>
        <property name="driverClass" value="${jdbc.driverClass}"></property>
        <property name="user" value="${jdbc.user}"></property>
        <property name="password" value="${jdbc.password}"></property>
    </bean>


    <context:component-scan base-package="com.liuzhan">
        <!-- 不能掃描控制器 -->
    <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"/> </context:component-scan>


    <!-- 配置和mybatis的整合 -->
    <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
        <!-- 指定mybatis 全局配置文件的位置 -->
        <property name="configLocation" value="classpath:mybatis-config.xml"></property>
        <property name="dataSource" ref="pooledDataSource"></property>
        <!-- 指定mybatismapper文件的位置 -->
<!--        <property name="mapperLocations" value="classpath:mapper/*.xml"></property>-->
    </bean>


    <!-- 配置掃描器,將mybatis接口的實(shí)現(xiàn)加入到ioc容器中 -->
    <bean class="tk.mybatis.spring.mapper.MapperScannerConfigurer">
        <!-- 掃描所有的dao接口 -->
        <property name="basePackage" value="com.liuzhan.dao"></property>
    </bean>

    <!-- 事務(wù)控制的配置 -->

    <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <!-- 控制數(shù)據(jù)源 -->
        <property name="dataSource" ref="pooledDataSource"></property>
    </bean>

    <aop:config>
        <!-- 切入點(diǎn)表達(dá)式 -->
        <aop:pointcut expression="execution(* com.liuzhan.service..*(..) )" id="txPoint"/>
        <!-- 配置事務(wù) -->
        <aop:advisor advice-ref="txAdvice" pointcut-ref="txPoint"/>
    </aop:config>
    <!-- 配置事務(wù)增強(qiáng)  事務(wù)如何切入 -->
    <tx:advice id="txAdvice">

        <tx:attributes>
            <!-- 所有方法都是事務(wù)方法 -->
            <tx:method name="*"/>
            <!-- 以get開(kāi)頭的所有方法 -->
            <tx:method name="get*" read-only="true"/>
        </tx:attributes>
    </tx:advice>





    <!-- shiro -->

    <!-- 配置自定義Realm -->
    <bean id="myRealm" class="com.liuzhan.relams.ShiroRealm"/>
    <!-- 安全管理器 -->
    <bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
        <property name="realm" ref="myRealm"/>
    </bean>
    <!-- Shiro過(guò)濾器 核心-->
    <bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
        <!-- Shiro的核心安全接口,這個(gè)屬性是必須的 -->
        <property name="securityManager" ref="securityManager"/>
        <!-- 身份認(rèn)證失敗,則跳轉(zhuǎn)到登錄頁(yè)面的配置 -->
        <property name="loginUrl" value="/login.jsp"/>

        <!-- 權(quán)限認(rèn)證失敗,則跳轉(zhuǎn)到指定頁(yè)面 -->
        <property name="unauthorizedUrl" value="/noPermission.jsp"/>

        <!-- Shiro連接約束配置,即過(guò)濾鏈的定義 -->
        <property name="filterChainDefinitions">
            <value>
                <!--設(shè)置jsp文件可以匿名訪問(wèn),靜態(tài)文件,如js\html\css\img等
                -->
                <!--login/**= anon
                /css/**=anon
                /html/**=anon
                /images/**=anon
                /js/**=anon
                -->


                /noPermission.jsp=anon
                <!--anon 表示匿名訪問(wèn),不需要認(rèn)證以及授權(quán)-->
                /login.jsp=anon
                <!-- 由于該請(qǐng)求http://localhost:8080/ssm_shiro_war_exploded/login是執(zhí)行認(rèn)證的請(qǐng)求路徑,因此不能被攔截,不然永遠(yuǎn)無(wú)法執(zhí)行認(rèn)證 -->
                /login = anon
                <!-- logout 表示退出,當(dāng)有/logout請(qǐng)求時(shí),會(huì)執(zhí)行退出,清除用戶信息及角色和權(quán)限信息-->
                /logout = logout



<!--             先登錄驗(yàn)證 -->
                /**=authc

                <!-- 角色驗(yàn)證方式一(單個(gè)角色),判斷該用戶是否擁有admin角色 -->
                <!--  注意,登錄驗(yàn)證時(shí)不會(huì)執(zhí)行該過(guò)濾規(guī)則,權(quán)限驗(yàn)證會(huì)執(zhí)行user過(guò)濾規(guī)則,如果沒(méi)有roles條件,默認(rèn)是所有權(quán)限          -->
                /**=user,roles[admin]
                <!-- 或/**=roles[admin]  -->
                <!-- 角色驗(yàn)證方式二(多個(gè)角色),判斷該用戶是否擁有admin、user角色 -->
<!--                /**=roles["admin,user"]-->
                <!-- /**放在最下邊,如果一個(gè)url有多個(gè)過(guò)慮器則多個(gè)過(guò)慮器中間用逗號(hào)分隔,如:/** = user,roles[admin]-->

            </value>
        </property>

    </bean>
    <!-- 保證實(shí)現(xiàn)了Shiro內(nèi)部lifecycle函數(shù)的bean執(zhí)行 -->
    <bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>
    <!-- 開(kāi)啟Shiro注解 -->
    <bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"
          depends-on= "lifecycleBeanPostProcessor"/>
    <bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
        <property name="securityManager" ref="securityManager"/>
    </bean>
</beans>

4.自定義realm(內(nèi)部定義認(rèn)證和授權(quán)的邏輯代碼)

怎么在shiro使用ssm框架

package com.liuzhan.relams;

import com.liuzhan.entity.Users;
import com.liuzhan.service.UserService;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;

import java.util.HashSet;
import java.util.List;
import java.util.Set;

public class ShiroRealm extends AuthorizingRealm {

    @Autowired
    UserService userService;


    /**
     * 用于授權(quán)。
     * @param principalCollection
     * @return
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        System.out.println("開(kāi)始授權(quán)");
        String uName = principalCollection.getPrimaryPrincipal().toString() ;
        SimpleAuthorizationInfo info = new SimpleAuthorizationInfo() ;
        List<Users> list=userService.loginCheck(uName);
        //查詢當(dāng)前用戶的角色,放在roleName中
        Set<String> roleName = new HashSet<>();
        roleName.add(list.get(0).getRole());

        //查詢角色具有的權(quán)限,放在permissions中
        Set<String> permissions = new HashSet<>();
        permissions.add("manage other users");

        //把角色和權(quán)限放在授權(quán)類的對(duì)象中
        info.addRole(list.get(0).getRole());
        info.addStringPermission("manage other users");

        System.out.println("當(dāng)前用戶角色:"+info.getRoles());
        return info;
    }




    //認(rèn)證
    //用戶輸入用戶名和密碼后,在controller調(diào)用login(token),進(jìn)行認(rèn)證,這邊通過(guò)用戶名查詢密碼
    //和token中用戶名和密碼進(jìn)行比對(duì),成功認(rèn)證或失敗
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {

        System.out.println("開(kāi)始登錄認(rèn)證");

        //獲取用戶名,去數(shù)據(jù)庫(kù)取對(duì)應(yīng)密碼
        String uName = (String) authenticationToken.getPrincipal();
        List<Users> list=userService.loginCheck(uName);

        if(list.size()>0){
            System.out.println("用戶存在");
            String uPwd=list.get(0).getuPwd();
            // 用戶名存在,去數(shù)據(jù)庫(kù)中去獲取密碼
            // 然后和token的用戶名和密碼對(duì)比
            // 第三個(gè)參數(shù)是選擇realm,當(dāng)有多個(gè)自定義realm時(shí)有用
            SimpleAuthenticationInfo info=new
                    SimpleAuthenticationInfo(uName, uPwd, "ShiroRealm");
            return info;
        }
        else{
            System.out.println("用戶不存在");
            return null;
        }

    }
}

5.controller中相關(guān)代碼

怎么在shiro使用ssm框架

package com.liuzhan.controller;

import com.liuzhan.entity.Users;
import com.liuzhan.service.UserService;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;



@Controller
public class UserController {

    @Autowired
    UserService userService;

    @RequestMapping("/login")
    public String loginCheck(Users users){

        Subject subject=SecurityUtils.getSubject();
        if(!subject.isAuthenticated()) {
            UsernamePasswordToken token=new UsernamePasswordToken(users.getuName(),users.getuPwd());
            token.setRememberMe(true);
            try {
                //執(zhí)行登錄,會(huì)調(diào)用認(rèn)證方法,如果認(rèn)證失敗,會(huì)拋出異常,執(zhí)行catch
                subject.login(token);
            } catch (AuthenticationException e) {
                // TODO Auto-generated catch block
                System.out.println("登錄失敗:"+e.getMessage());
                return "login";
            }
        }
        //login(token)認(rèn)證成功會(huì)執(zhí)行這些語(yǔ)句
        System.out.println("登錄成功");

        //這里如果直接 return "WEB-INF/jsp/index"的話,由于默認(rèn)轉(zhuǎn)發(fā),地址欄不變,還是http://localhost:8080/ssm_shiro_war_exploded/login
        //仍然執(zhí)行/login = anon過(guò)濾規(guī)則,不會(huì)執(zhí)行下面的權(quán)限驗(yàn)證過(guò)濾規(guī)則 /**=user,roles[admin]

        //因此需要使用重定向"redirect:index",才能讓 /**=user,roles[admin]過(guò)濾規(guī)則生效
        return "redirect:index";
    }

    @RequestMapping("/index")
    public String index() {
       return "WEB-INF/jsp/index";
    }
}

怎么在shiro使用ssm框架

怎么在shiro使用ssm框架

這里到dao service entity就不再粘貼代碼了

6.數(shù)據(jù)庫(kù)連接配置相關(guān)

怎么在shiro使用ssm框架

jdbc.jdbcUrl=jdbc:mysql://localhost:3306/ssm-shiro?useUnicode=true&characterEncoding=utf-8&serverTimezone=GMT%2B8
jdbc.driverClass=com.mysql.cj.jdbc.Driver
jdbc.user=root
jdbc.password=root

applicationContext.xml

怎么在shiro使用ssm框架

項(xiàng)目中用到的是通用mapper,實(shí)體類的類名和數(shù)據(jù)庫(kù)的表名對(duì)應(yīng),實(shí)體類的屬性和數(shù)據(jù)庫(kù)表的字段名對(duì)應(yīng)

怎么在shiro使用ssm框架

測(cè)試

運(yùn)行項(xiàng)目

怎么在shiro使用ssm框架

因?yàn)槲襰hiro過(guò)濾鏈配置的是只有角色為admin的能進(jìn)首頁(yè),角色為user不能進(jìn)首頁(yè),會(huì)被攔截(數(shù)據(jù)庫(kù)jake為admin,tom為user)

怎么在shiro使用ssm框架

運(yùn)行結(jié)果:

怎么在shiro使用ssm框架

怎么在shiro使用ssm框架

上述內(nèi)容就是怎么在shiro使用ssm框架,你們學(xué)到知識(shí)或技能了嗎?如果還想學(xué)到更多技能或者豐富自己的知識(shí)儲(chǔ)備,歡迎關(guān)注億速云行業(yè)資訊頻道。

向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI