隨筆-199  評(píng)論-203  文章-11  trackbacks-0

          (一)Hibernate的二級(jí)緩存策略的一般過程如下:

          1) 條件查詢的時(shí)候,總是發(fā)出一條select * from table_name where …. (選擇所有字段)這樣的SQL語句查詢數(shù)據(jù)庫,一次獲得所有的數(shù)據(jù)對(duì)象。

          2) 把獲得的所有數(shù)據(jù)對(duì)象根據(jù)ID放入到第二級(jí)緩存中。

          3) 當(dāng)Hibernate根據(jù)ID訪問數(shù)據(jù)對(duì)象的時(shí)候,首先從Session一級(jí)緩存中查;查不到,如果配置了二級(jí)緩存,那么從二級(jí)緩存中查;查不到,再查詢數(shù)據(jù)庫,把結(jié)果按照ID放入到緩存。

          4) 刪除、更新、增加數(shù)據(jù)的時(shí)候,同時(shí)更新緩存。

          Hibernate的二級(jí)緩存策略,是針對(duì)于ID查詢的緩存策略,對(duì)于條件查詢則毫無作用。為此,Hibernate提供了針對(duì)條件查詢的Query Cache。

          (二)什么樣的數(shù)據(jù)適合存放到第二級(jí)緩存中?

          1 很少被修改的數(shù)據(jù)

          2 不是很重要的數(shù)據(jù),允許出現(xiàn)偶爾并發(fā)的數(shù)據(jù)

          3 不會(huì)被并發(fā)訪問的數(shù)據(jù)

          4 參考數(shù)據(jù),指的是供應(yīng)用參考的常量數(shù)據(jù),它的實(shí)例數(shù)目有限,它的實(shí)例會(huì)被許多其他類的實(shí)例引用,實(shí)例極少或者從來不會(huì)被修改。

          (三)不適合存放到第二級(jí)緩存的數(shù)據(jù)?

          1 經(jīng)常被修改的數(shù)據(jù)

          2 財(cái)務(wù)數(shù)據(jù),絕對(duì)不允許出現(xiàn)并發(fā)

          3 與其他應(yīng)用共享的數(shù)據(jù)。

          實(shí)踐部分:

          使用EhCache配置二級(jí)緩存

          配置準(zhǔn)備:

          1)把ehcache-1.2.3.jar加入到當(dāng)前應(yīng)用的classpath中。

          2)在hibernate.cfg.xml文件中加入EhCache緩存插件的提供類。

          1. <!--配置緩存插件 -->   
          2. <property name="hibernate.cache.provider_class">   
          3.     org.hibernate.cache.EhCacheProvider   
          4. </property>  

          3)挎貝ehcache.xml文件到類路徑(項(xiàng)目工程的src目錄下),這個(gè)文件在Hibernate安裝目錄的etc下。

          配置步驟:

          Hibernate允許在類和集合的粒度上設(shè)置第二級(jí)緩存。在映射文件中,<class>和<set>元素都有一個(gè)<cache>子元素,這個(gè)子元素用來配置二級(jí)緩存。
          示例:以category(產(chǎn)品類別)和product(產(chǎn)品)的映射為例:

          1) 修改要配置緩存的那個(gè)持久化類的對(duì)象關(guān)系映射文件:

          Category.hbm.xml

          <?xml version="1.0" encoding="utf-8"?>  

          <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"  
          " <hibernate-mapping>  
              <class name="org.qiujy.domain.cachedemo.Category" table="categories">  
                 <!—  
                       配置緩存,必須緊跟在class元素后面  
                      對(duì)緩存中的Category對(duì)象采用讀寫型的并發(fā)訪問策略  
                  -->  
                 <cache usage="read-write"/>  
                  
                 <id name="id" type="java.lang.Long">  
                     <column name="id" />  
                     <generator class="native" />  
                 </id>  
                 <!-- 配置版本號(hào),必須緊跟在id元素后面 -->  
                 <version name="version" column="version" type="java.lang.Long" />  
                  
                 <property name="name" type="java.lang.String">  
                     <column name="name" length="32" not-null="true"/>  
                 </property>  
                  
                 <property name="description" type="java.lang.String">  
                     <column name="description" length="255"/>  
                 </property>  
                  
                 <set name="products" table="products" cascade="all" inverse="true">  
                     <!-- Hibernate只會(huì)緩存對(duì)象的簡單屬性的值,  
                 要緩存集合屬性,必須在集合元素中也加入<cache>子元素  
                 而Hibernate僅僅是把與當(dāng)前持久對(duì)象關(guān)聯(lián)的對(duì)象的OID存放到緩存中。  
          如果希望把整個(gè)關(guān)聯(lián)的對(duì)象的所有數(shù)據(jù)都存入緩存,  
          則要在相應(yīng)關(guān)聯(lián)的對(duì)象的映射文件中配置<cache>元素  
                     -->  
                     <cache usage="read-write"/>  
                      
                     <key column="categoryId" not-null="true"/>  
                     <one-to-many class="org.qiujy.domain.cachedemo.Product"/>  
                 </set>  
                  
              </class>  
          </hibernate-mapping>

          Product.hbm.xml

          <?xml version="1.0" encoding="utf-8"?>  
          <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"  
          " <hibernate-mapping>  
              <class name="org.qiujy.domain.cachedemo.Product" table="products">  
                  
                 <cache usage="read-write"/>  
                  
                 <id name="id" type="java.lang.Long">  
                     <column name="id" />  
                     <generator class="native" />  
                 </id>  
                 <!-- 配置版本號(hào),必須緊跟在id元素后面 -->  
                 <version name="version" column="version" type="java.lang.Long" />  
                  
                 <property name="name" type="java.lang.String">  
                     <column name="name" length="32" not-null="true"/>  
                 </property>  
                  
                 <property name="description" type="java.lang.String">  
                     <column name="description" length="255"/>  
                 </property>  
                  
                 <property name="unitCost" type="java.lang.Double">  
                     <column name="unitCost" />  
                 </property>  
                  
                 <property name="pubTime" type="java.util.Date">  
                     <column name="pubTime" not-null="true" />  
                 </property>  
                  
                 <many-to-one name="category"  
                          column="categoryId"  
                         class="org.qiujy.domain.cachedemo.Category"  
                         cascade="save-update"  
                          not-null="true">  
                  </many-to-one>  
                  
              </class>  
          </hibernate-mapping>

          2)編輯ehcache.xml文件:

          <ehcache>  
              <diskStore path="c:\\ehcache\"/>  
              <defaultCache  
                  maxElementsInMemory="10000"  
                  eternal="false"  
                  timeToIdleSeconds="120"  
                  timeToLiveSeconds="120"  
                  overflowToDisk="true"    
                  />  
                   
              <!-- 設(shè)置Category類的緩存的數(shù)據(jù)過期策略 -->  
              <cache name="org.qiujy.domain.cachedemo.Category"  
                  maxElementsInMemory="100"  
                  eternal="true"  
                  timeToIdleSeconds="0"  
                  timeToLiveSeconds="0"  
                  overflowToDisk="false"  
                  />  
                   
               <!-- 設(shè)置Category類的products集合的緩存的數(shù)據(jù)過期策略 -->  
               <cache name="org.qiujy.domain.cachedemo.Category.products"  
                  maxElementsInMemory="500"  
                  eternal="false"  
                  timeToIdleSeconds="300"  
                  timeToLiveSeconds="600"  
                  overflowToDisk="true"  
                  />  
                   
              <cache name="org.qiujy.domain.cachedemo.Product"  
                  maxElementsInMemory="500"  
                  eternal="false"  
                  timeToIdleSeconds="300"  
                  timeToLiveSeconds="600"  
                  overflowToDisk="true"  
                  />  
               
          </ehcache>

          在Spring托管的Hibernate中使用二級(jí)緩存 1.在spring的配置文件中,hibernate部分加入 xml 代碼 org.hibernate.cache.EhCacheProvider true 2.為HBM表設(shè)置cache策略 xml 代碼 3.在DAO中,調(diào)用find方法查詢之前,設(shè)置使用緩存 Java代碼 getHibernateTemplate().setCacheQueries(true); 補(bǔ)充: 如果不設(shè)置“查詢緩存”,那么hibernate只會(huì)緩存使用load()方法獲得的單個(gè)持久化對(duì)象,如果想緩存使用findall()、list()、Iterator()、createCriteria()、createQuery()等方法獲得的數(shù)據(jù)結(jié)果集的話,就需要設(shè)置 hibernate.cache.use_query_cache true 才行。

          posted on 2009-06-23 17:32 Werther 閱讀(1708) 評(píng)論(2)  編輯  收藏 所屬分類: 21.Hibernate

          評(píng)論:
          # re: Hibernate中二級(jí)緩存的配置和使用 2009-06-24 20:22 | 心夢(mèng)帆影
          學(xué)習(xí)了,謝謝你這么好的文章。有個(gè)問題想請(qǐng)教一下:
          “并發(fā)訪問的數(shù)據(jù)”是什么意思?多個(gè)人同時(shí)訪問同一數(shù)據(jù)是不是并發(fā)訪問?  回復(fù)  更多評(píng)論
            
          # re: Hibernate中二級(jí)緩存的配置和使用 2009-06-24 21:25 | Werther
          @心夢(mèng)帆影
          同時(shí)訪問一種資源的用戶被視為并發(fā)訪問數(shù)據(jù),也就是你所說的,多個(gè)人同時(shí)訪問同一個(gè)數(shù)據(jù).  回復(fù)  更多評(píng)論
            
          主站蜘蛛池模板: 德令哈市| 自贡市| 威远县| 北京市| 娱乐| 阜康市| 栖霞市| 股票| 德阳市| 绥滨县| 旬阳县| 陈巴尔虎旗| 林芝县| 温州市| 宜章县| 博爱县| 中阳县| 休宁县| 沂源县| 南城县| 合肥市| 博罗县| 北碚区| 罗山县| 六安市| 临汾市| 灵山县| 民权县| 如东县| 白城市| 虎林市| 甘洛县| 江西省| 新和县| 蒙自县| 大城县| 缙云县| 澄城县| 饶河县| 龙口市| 宜宾县|