Ehcache二級緩存,查詢緩存,分佈式緩存總結

二級緩存和查詢緩存都至關於一個map
二級緩存緩存的keyidvalue爲實體對象。通常load(),iterate()使用到二級緩存,list()須要結合查詢緩存使用。iterate()和list()區別以下:
iterate()不須要開啓查詢緩存,它首先發出一個sqlselect s.id from Student s去數據庫把id屬性列表取出來,而後再根據id列表一個一個load(),若是緩存有從緩存取,若是緩存沒有就從數據庫取:select s.id,s.name,s.classid from     Student s where s.id=?,取出後再存入二級緩存。Iterate總會發出取id列表的語句。
List()須要開啓查詢緩存,它首先發出一個sqlselect s.id,s.name,s.classid from Student s…」去數據庫取出全部相關實體,並將這些實體存入二級緩存,將此sql語句及一些相關信息做爲keyid列表做爲值,第二次查詢這條語句時就會去根據sql語句及相關信息去key裏找,若是有就會把id列表取出一個一個load(),接下來就和iterate同樣了。List通常只有第一次發發出取實體列表的語句,之後的id列表就會去查詢緩存取id列表,不會再發出sql語句。
 
前提:執行同一hql語句,如:select s from Student s
1.  關閉查詢緩存,開啓二級緩存時:
第二次查詢屬性時iterate只會發出獲取id列表的sqllist會發出和第一次同樣的請求實體的sql
2.  開啓查詢緩存,開啓二級緩存
第二次查詢屬性時iterate只會發出獲取id列表的sqllist不發sql
以上說明iterate只和二級緩存有關,list和二級緩存和查詢緩存都有關。
 
查詢緩存的key是一個QueryKey(其屬性以下),valueid集合。

  
  
           
  
  
  1. public class QueryKey implements Serializable { 
  2.    private final String sqlQueryString;//sql語句 
  3.    private final Type[] types; 
  4.    private final Object[] values; 
  5.    private final Integer firstRow;//要查詢的起始數 
  6.    private final Integer maxRows;//要查詢的個數 
  7.    private final Map namedParameters; 
  8.    private final EntityMode entityMode; 
  9.    private final Set filters; 
  10.    private final int hashCode; 
  11.    ...... 
果以上屬性中有一個不一樣,查詢緩存就不會命中。使用list()時,若是是第一次,查詢緩存取出實體列表,而後從實體列表中提取出id列表做爲value。若是是查詢緩存命中,就會根據QueryKey取出id列表,而後根據id列表去二級緩存中load()對象,若是二級緩存中沒有哪一個對象,就會根據id去數據庫查詢,二級緩存中沒有n個對象就會去數據庫查詢n次:select p from pojo p where id=?,所以就會有機會出現傳說中n+1問題。
在查詢緩存中,查詢緩存緩存普通屬性,即對於屬性的查詢,value值爲要查詢的屬性列表,對於實體,value值爲實體的id列表,而對於屬性的查詢因爲從value中直接能夠查出就不會用到二級緩存,但對於實體的查詢,必須結合二級緩存使用。下面對此進行說明:
前提:執行同一hql語句,如:select s from Student sselect s.name from Student s
1.  開啓查詢緩存,關閉二級緩存時:
第二次查詢屬性時不會發出sql,第一次查詢實體時會發出sql
2.  開啓查詢緩存,開啓二級緩存
第二次查詢屬性,實體時都不發sql
 
 
對於Ehcache分佈式緩存,好像查詢緩存不能更新:
在同一系統中,當用Hibernate的方式修改表數據(save,update,delete等等),這時EhCache會自動把緩存中關於此表的全部緩存所有刪除掉(這樣能達到同步)。但對於兩個以上系統部署在不一樣機子上,並在他們之間配置了ehcache的分佈式緩存,當A系統修改表數據(save,update,delete)後,b系統會更新查詢緩存嗎?
答:好像是不能的,即ehcache的分佈式緩存對查詢緩存無效。(我在項目中配置了Ehcache的分佈式緩存,二級緩存能夠生效,但查詢緩存不能更新。是否是一個系統中的Hibernate不可以識別其餘系統中hibernate是否進行了save,update,delete操做?而Ehcache也沒對此進行整合,望知道的大牛給說一下。)
相關文章
相關標籤/搜索