Query q1 = s.createQuery(hql); Emp e1 = (Emp) q1.uniqueResult(); System.out.println("e1:" + e1.getEname()); Emp e2 = (Emp) s.get(Emp.class, 7369); System.out.println("e2:" + e2.getEname());
※此時get可以讀到快取,看起來好像ok
Emp e2 = (Emp) s.get(Emp.class, 7369); System.out.println("e2:" + e2.getEname()); Query q1 = s.createQuery(hql); q1.setCacheable(true); Emp e1 = (Emp) q1.uniqueResult(); System.out.println("e1:" + e1.getEname());
※但把get放在前面就讀不到了,看起來Query會放到快取裡,所以get讀得到
※但相反後Query無法讀取get的快取,看起來Query不去讀取快取的樣子
※我試Query、Criteria都是這樣的結果,但SQLQuery怎麼放都不行
想讓Query讀得到,必需在hibernate.cfg.xml設定
<property name="hibernate.cache.use_second_level_cache">true</property> <property name="hibernate.cache.provider_class">org.hibernate.cache.EhCacheProvider</property> <property name="hibernate.QueryCacheEnabled">true</property> <property name="hibernate.cache.use_query_cache">true</property>
※前三行是二級快取的設定,後面才是現在要的設定
※這個設定一定要設二級快取,不然執行時會報「org.hibernate.cache.NoCachingEnabledException: Second-level cache is not enabled for usage [hibernate.cache.use_second_level_cache | hibernate.cache.use_query_cache]」的錯,也就是Query只能用二級快取
Session s = HibernateUtil2.getSession(); final String sql = "select * from Emp where empno = 7369"; final String hql = "from Emp where empno = 7369"; try { Query q1 = s.createSQLQuery(sql).addScalar("ename", Hibernate.STRING); q1.setCacheable(true); System.out.println("e1:" + q1.uniqueResult()); Query q2 = s.createSQLQuery(sql).addScalar("ename", Hibernate.STRING); q2.setCacheable(true); System.out.println("e2:" + q2.uniqueResult()); Query q3 = s.createQuery(hql); q3.setCacheable(true); Emp e3 = (Emp) q3.uniqueResult(); System.out.println("e3:" + e3.getEname()); Query q4 = s.createQuery(hql); q4.setCacheable(true); Emp e4 = (Emp) q4.uniqueResult(); System.out.println("e4:" + e4.getEname()); Criteria q5 = s.createCriteria(Emp.class); q5.setCacheable(true); q5.add(Restrictions.eq("empno", 7369)); Emp e5 = (Emp) q5.uniqueResult(); System.out.println("e5:" + e5.getEname()); Criteria q6 = s.createCriteria(Emp.class); q6.setCacheable(true); q6.add(Restrictions.eq("empno", 7369)); Emp e6 = (Emp) q6.uniqueResult(); System.out.println("e6:" + e6.getEname()); Emp xxx = (Emp) s.get(Emp.class, 7369); System.out.println("xxx:" + xxx.getEname()); } catch (Exception e) { System.err.println("例外錯誤!"); e.printStackTrace(); } finally { if (s.isOpen()) { s.close(); } }
※只有設定還不夠,還要在程式寫setCacheable(true),而且每一個Query都要,不然都抓不到快取
※每個快取不能混用,如SQLQuery對SQLQuery、Criteria對Criteria、Query對Query,混用一樣也是抓不到快取
※以第二張圖的程式碼,加上setCacheable(true),還是抓不到快取
沒有留言:
張貼留言