【发布时间】:2015-09-17 09:31:54
【问题描述】:
我在 Wildfly 8.2 上使用 Spring Data JPA、Hibernate 4.3.10.Final、Ehcache。我想测试应用服务器如何处理缓存中的所有数据。
问题是:是否可以默认为所有扫描的实体启用二级缓存?
实际上,我想避免在每个实体上添加@Cache(因为该项目有 100 多个)。
JPA 属性
... data source definition ...
<property name="sharedCacheMode" value="ALL" />
休眠属性
<prop key="hibernate.generate_statistics">true</prop>
<prop key="hibernate.cache.use_second_level_cache">true</prop>
<prop key="hibernate.cache.use_query_cache">false</prop>
<prop key="hibernate.cache.region.factory_class">org.hibernate.cache.ehcache.EhCacheRegionFactory</prop>
<prop key="net.sf.ehcache.configurationResourceName">/ehcache.xml</prop>
ehcache.xml
<?xml version="1.0" encoding="UTF-8"?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="http://ehcache.org/ehcache.xsd"
updateCheck="true"
monitoring="autodetect"
dynamicConfig="true">
<diskStore path="java.io.tmpdir/ehcache" />
<defaultCache maxElementsInMemory="1000000000"
eternal="true"
overflowToDisk="false"
diskPersistent="false"
diskExpiryThreadIntervalSeconds="120"
memoryStoreEvictionPolicy="LRU"
statistics="true"
>
</defaultCache>
<!--
<cache name="org.hibernate.cache.internal.StandardQueryCache"
eternal="false"
timeToLiveSeconds="120">
<persistence strategy="localTempSwap"/>
</cache> -->
</ehcache>
编辑:
按照 Dragan Bozanovic 的建议尝试了 <prop key="javax.persistence.sharedCache.mode">ALL</prop>,但它不影响该过程。
这是 SELECT e FROM MyEntity e 执行 2 次的统计日志:
17:00:00,597 | INFO | StatisticalLoggingSessionE:275 | | Session Metrics {
71157 nanoseconds spent acquiring 1 JDBC connections;
0 nanoseconds spent releasing 0 JDBC connections;
145393 nanoseconds spent preparing 1 JDBC statements;
386233 nanoseconds spent executing 1 JDBC statements;
0 nanoseconds spent executing 0 JDBC batches;
822075 nanoseconds spent performing 41 L2C puts;
0 nanoseconds spent performing 0 L2C hits;
0 nanoseconds spent performing 0 L2C misses;
0 nanoseconds spent executing 0 flushes (flushing a total of 0 entities and 0 collections);
0 nanoseconds spent executing 0 partial-flushes (flushing a total of 0 entities and 0 collections)
}
17:00:00,597 | INFO | StatisticalLoggingSessionE:275 | | Session Metrics {
63973 nanoseconds spent acquiring 1 JDBC connections;
0 nanoseconds spent releasing 0 JDBC connections;
127262 nanoseconds spent preparing 1 JDBC statements;
282918 nanoseconds spent executing 1 JDBC statements;
0 nanoseconds spent executing 0 JDBC batches;
452598 nanoseconds spent performing 41 L2C puts;
0 nanoseconds spent performing 0 L2C hits;
0 nanoseconds spent performing 0 L2C misses;
0 nanoseconds spent executing 0 flushes (flushing a total of 0 entities and 0 collections);
0 nanoseconds spent executing 0 partial-flushes (flushing a total of 0 entities and 0 collections)
}
返回了 41 行,这是正确的。但是我看到41 L2C puts 2 次,不应该是41 L2C puts 然后是41 L2C hits 吗?
【问题讨论】:
-
配置似乎生效了 - 您正在将实体存储到 L2 缓存中。关于统计信息,请尝试按 id(
entityManager.find(MyEntity.class, id),或 Spring Data 中的等效项)读取实体。这里你正在执行查询,Hibernate 必须在数据库中执行它。 -
与
.setHint("org.hibernate.cacheable", true)一起使用效果更好 :)。感谢您的帮助! -
您是否将该提示添加到查询中?如果是这样,您真的希望查询可缓存吗?既然您已将
use_query_cache设置为false,为什么它会起作用? -
是的,我做到了。为此,我将
use_query_cache切换为true。我不想让所有查询都可缓存,而是在缓存中加载所有实体以查看内存使用情况。