首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 綜合教學

Hibernate 三大持久化狀態與兩級緩存機制深度解析

     編輯:Java 綜合教學

三大持久化狀態

狀態定義OIDSession 緩存資料庫記錄典型場景
瞬時態new 出來,未關聯 Session無無無new User()
持久態關聯 Session,納入一級緩存有有有(或即將同步)session.save(user)
游離態Session 關閉/清理/evict,脫離管理有無有session.close() 後

狀態轉換圖解

new User()  ──save()──▶ 持久態 ──close()/evict()──▶ 游離態
    ▲                                      │
    │                                      ▼
    └────── update()/saveOrUpdate() ◀── 游離態

關鍵特性:持久態自動髒檢查

Session session = sf.openSession();
Transaction tx = session.beginTransaction();

User u = session.get(User.class, 1L);  // 持久態
u.setName("New Name");                 // 修改屬性
// 無需呼叫 update()!
tx.commit();  // 提交時自動發送 UPDATE SQL
session.close();

原理:Session 快照機制,提交時比較快照與當前狀態,生成 UPDATE。

一級緩存(Session 級)

  • 生命週期:與 Session 同生共死,預設開啟,不可關閉。
  • 作用域:事務級/請求級。
  • 核心 API:
      • evict(obj):移除指定對象
      • clear():清空整個緩存
  • 驗證:同一 Session 內重複 get() 同一 ID,只發 1 條 SQL。

二級緩存(SessionFactory 級)

啟用步驟

  1. 配置提供者(以 EhCache 3.x 為例)
    hibernate.cache.use_second_level_cache=true
    hibernate.cache.region.factory_class=org.hibernate.cache.ehcache.EhCacheRegionFactory
  2. 聲明實體緩存策略
    註解方式:@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
    XML 方式:<class-cache class="..." usage="read-write"/>
  3. 配置 ehcache.xml
    設定 maxEntriesLocalHeap、timeToLiveSeconds、overflowToDisk 等。

四種併發策略選型

策略適用場景特點
READ_ONLY從不修改的參考數據(字典、配置)最高效、最安全
NONSTRICT_READ_WRITE極少修改、允許極小概率臟讀無鎖、性能好
READ_WRITE常規業務數據、需強一致性軟鎖、支援事務隔離
TRANSACTIONALJTA 環境、需 XA 事務完全事務語義、效能最低

二級緩存工作流程

  1. ID 查詢(get/load) → 一級緩存 → 二級緩存 → 資料庫
  2. 條件查詢(list/iterate) → 不走二級緩存(除非開啟查詢緩存)
  3. 增刪改 → 同步更新一級、二級緩存

查詢緩存

  • 針對普通屬性/標量結果集緩存;實體查詢僅緩存 ID,實體仍走二級緩存。
  • 啟用:hibernate.cache.use_query_cache=true + query.setCacheable(true)。
  • 依賴二級緩存,建議同時開啟。

什麼數據適合進二級緩存?

✅ 適合❌ 不適合
字典表、配置表、郵編、貨幣匯率訂單、庫存、賬戶餘額(高併發寫入)
權限菜單、組織架構(讀多寫少)跨應用共享表(緩存一致性難保證)
靜態參考數據(幾乎不變)財務核心數據(零容忍臟讀)

緩存清理 API

// SessionFactory 級
sf.evict(Entity.class);           // 清除某實體所有
sf.evict(Entity.class, id);       // 清除指定 ID
sf.evictCollection("Entity.field"); // 清除集合緩存

總結

掌握 三態轉換 是用好 Hibernate 的前提;一級緩存自動透明,二級緩存需顯式配置策略。生產環境建議:
1. 參考數據 → READ_ONLY + 二級緩存
2. 核心業務實體 → READ_WRITE + 謹慎開啟二級緩存
3. 複雜報表查詢 → 關閉二級/查詢緩存,走原生 SQL + 手動分頁
4. 監控緩存命中率(EhCache/JMX),命中率 < 80% 時重新評估策略。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved