- Hibernate 教程
- Hibernate - 首頁
- ORM - 概述
- Hibernate - 概述
- Hibernate - 架構
- Hibernate - 環境
- Hibernate - 配置
- Hibernate - 會話
- Hibernate - 持久化類
- Hibernate - 對映檔案
- Hibernate - 對映型別
- Hibernate - 示例
- Hibernate - O/R 對映
- Hibernate - 級聯型別
- Hibernate - 註解
- Hibernate - 查詢語言
- Hibernate - Criteria 查詢
- Hibernate - 原生 SQL
- Hibernate - 快取
- Hibernate - 實體生命週期
- Hibernate - 批次處理
- Hibernate - 攔截器
- Hibernate - ID 生成器
- Hibernate - 儲存圖片
- Hibernate - log4j 整合
- Hibernate - Spring 整合
- Hibernate - Struts 2 整合
- Hibernate - Web 應用程式
- 對映表示例
- Hibernate - 表繼承策略(每個層次結構一張表)
- Hibernate - 表繼承策略(每個具體類一張表)
- Hibernate - 表繼承策略(每個子類一張表)
- Hibernate 有用資源
- Hibernate - 常見問題解答
- Hibernate - 快速指南
- Hibernate - 有用資源
- Hibernate - 討論
Hibernate - 快取
快取是一種增強系統性能的機制。它是一個位於應用程式和資料庫之間的緩衝記憶體。快取記憶體儲存最近使用的資料項,以便儘可能減少資料庫訪問次數。
快取對 Hibernate 也很重要。它利用瞭如下所述的多級快取方案:
一級快取
一級快取是 Session 快取,是所有請求都必須經過的強制快取。Session 物件在將物件提交到資料庫之前,會將其保留在自己控制之下。
如果您對某個物件發出多個更新操作,Hibernate 會嘗試儘可能延遲執行更新操作,以減少發出的更新 SQL 語句的數量。如果您關閉 Session,則所有正在快取的物件都會丟失,並在資料庫中持久化或更新。
二級快取
二級快取是可選快取,在嘗試在二級快取中查詢物件之前,始終會先查詢一級快取。二級快取可以在每個類和每個集合的基礎上進行配置,主要負責跨 Session 快取物件。
任何第三方快取都可以與 Hibernate 一起使用。提供了org.hibernate.cache.CacheProvider介面,必須實現該接口才能為 Hibernate 提供快取實現的控制代碼。
查詢級快取
Hibernate 還為查詢結果集實現了快取,該快取與二級快取緊密整合。
這是一個可選功能,需要兩個額外的物理快取區域來儲存快取的查詢結果以及上次更新表的時間戳。這僅適用於經常使用相同引數執行的查詢。
二級快取
Hibernate 預設使用一級快取,您無需執行任何操作即可使用一級快取。讓我們直接進入可選的二級快取。並非所有類都受益於快取,因此能夠停用二級快取非常重要。
Hibernate 二級快取的設定分為兩個步驟。首先,您必須決定使用哪種併發策略。之後,您使用快取提供程式配置快取過期和物理快取屬性。
併發策略
併發策略是一種中介,負責將資料項儲存在快取中並從快取中檢索它們。如果您要啟用二級快取,則必須為每個持久化類和集合決定使用哪種快取併發策略。
事務型 - 在很少出現更新的情況下,對於主要用於讀取的資料,如果關鍵是要防止併發事務中的陳舊資料,請使用此策略。
讀寫型 - 在很少出現更新的情況下,對於主要用於讀取的資料,如果關鍵是要防止併發事務中的陳舊資料,請再次使用此策略。
非嚴格讀寫型 - 此策略不保證快取和資料庫之間的一致性。如果資料幾乎從不更改並且出現少量陳舊資料的可能性並不關鍵,請使用此策略。
只讀型 - 適用於從不更改資料的併發策略。僅對參考資料使用它。
如果我們要對Employee類使用二級快取,讓我們新增所需的對映元素來告訴 Hibernate 使用讀寫策略快取 Employee 例項。
<?xml version = "1.0" encoding = "utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name = "Employee" table = "EMPLOYEE">
<meta attribute = "class-description">
This class contains the employee detail.
</meta>
<cache usage = "read-write"/>
<id name = "id" type = "int" column = "id">
<generator class="native"/>
</id>
<property name = "firstName" column = "first_name" type = "string"/>
<property name = "lastName" column = "last_name" type = "string"/>
<property name = "salary" column = "salary" type = "int"/>
</class>
</hibernate-mapping>
usage="read-write"屬性告訴 Hibernate 對定義的快取使用讀寫併發策略。
快取提供程式
在考慮了併發策略之後,下一步是使用快取候選類選擇快取提供程式。Hibernate 強制您為整個應用程式選擇一個快取提供程式。
| 序號 | 快取名稱和描述 |
|---|---|
| 1 |
EHCache 它可以快取到記憶體或磁碟,並支援叢集快取,並且支援可選的 Hibernate 查詢結果快取。 |
| 2 |
OSCache 支援將快取到單個 JVM 中的記憶體和磁碟,並具有豐富的過期策略和查詢快取支援。 |
| 3 |
warmCache 基於 JGroups 的叢集快取。它使用叢集失效,但不支援 Hibernate 查詢快取。 |
| 4 |
JBoss Cache 一個完全事務性的複製叢集快取,也基於 JGroups 多播庫。它支援複製或失效、同步或非同步通訊以及樂觀和悲觀鎖定。支援 Hibernate 查詢快取。 |
並非每個快取提供程式都與每種併發策略相容。以下相容性矩陣將幫助您選擇合適的組合。
| 策略/提供程式 | 只讀型 | 非嚴格讀寫型 | 讀寫型 | 事務型 |
|---|---|---|---|---|
| EHCache | X | X | X | |
| OSCache | X | X | X | |
| SwarmCache | X | X | ||
| JBoss Cache | X | X |
您將在 hibernate.cfg.xml 配置檔案中指定快取提供程式。我們選擇 EHCache 作為我們的二級快取提供程式:
<?xml version = "1.0" encoding = "utf-8"?>
<!DOCTYPE hibernate-configuration SYSTEM
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name = "hibernate.dialect">
org.hibernate.dialect.MySQLDialect
</property>
<property name = "hibernate.connection.driver_class">
com.mysql.jdbc.Driver
</property>
<!-- Assume students is the database name -->
<property name = "hibernate.connection.url">
jdbc:mysql:///test
</property>
<property name = "hibernate.connection.username">
root
</property>
<property name = "hibernate.connection.password">
root123
</property>
<property name = "hibernate.cache.provider_class">
org.hibernate.cache.EhCacheProvider
</property>
<!-- List of XML mapping files -->
<mapping resource = "Employee.hbm.xml"/>
</session-factory>
</hibernate-configuration>
現在,您需要指定快取區域的屬性。EHCache 有自己的配置檔案ehcache.xml,該檔案應該位於應用程式的 CLASSPATH 中。ehcache.xml 中 Employee 類的快取配置可能如下所示:
<diskStore path="java.io.tmpdir"/> <defaultCache maxElementsInMemory = "1000" eternal = "false" timeToIdleSeconds = "120" timeToLiveSeconds = "120" overflowToDisk = "true" /> <cache name = "Employee" maxElementsInMemory = "500" eternal = "true" timeToIdleSeconds = "0" timeToLiveSeconds = "0" overflowToDisk = "false" />
就是這樣,現在我們為 Employee 類和 Hibernate 啟用了二級快取,現在只要您導航到 Employee 或按識別符號載入 Employee 時,Hibernate 就會命中二級快取。
您應該分析所有類併為每個類選擇合適的快取策略。有時,二級快取可能會降低應用程式的效能。因此,建議您首先在不啟用快取的情況下對應用程式進行基準測試,然後啟用適合您的快取並檢查效能。如果快取沒有提高系統性能,則啟用任何型別的快取都沒有意義。
查詢級快取
要使用查詢快取,您必須首先使用配置檔案中的hibernate.cache.use_query_cache="true"屬性啟用它。透過將此屬性設定為 true,您可以使 Hibernate 在記憶體中建立必要的快取來儲存查詢和識別符號集。
接下來,要使用查詢快取,您可以使用 Query 類的 setCacheable(Boolean)方法。例如:
Session session = SessionFactory.openSession();
Query query = session.createQuery("FROM EMPLOYEE");
query.setCacheable(true);
List users = query.list();
SessionFactory.closeSession();
Hibernate 還透過快取區域的概念支援非常細粒度的快取支援。快取區域是快取的一部分,並被賦予一個名稱。
Session session = SessionFactory.openSession();
Query query = session.createQuery("FROM EMPLOYEE");
query.setCacheable(true);
query.setCacheRegion("employee");
List users = query.list();
SessionFactory.closeSession();
此程式碼使用該方法告訴 Hibernate 將查詢儲存在快取的 employee 區域中並從中查詢查詢。