java – 在null值的情况下,OpenJpa查询缓存不会刷新
作者:互联网
我在OpenJpa二级缓存中遇到了一些问题.大多数情况下,缓存是有效的,但在一个特定的情况下它不起作用.这是一个不工作的场景,
当您的代码结果为null值时,它会将其存储到缓存中,然后它永远不会清除该值.虽然它仅在查询返回值时清除值.
这是我为从数据库中获取价值而编写的代码,
List<PartnerapiworkflowEntity> partnerapiworkflowEntityList = null;
try {
partnerapiworkflowEntityList = entityManager.createQuery("select p from someentity p where p.id = :Id and p.name = :name and " +
"p.code = :Code and p.operationname = :operationName")
.setParameter("Id", Id)
.setParameter("name", name)
.setParameter("code", Code)
.setParameter("operationName", operationName).getResultList();//.getSingleResult();
if(partnerapiworkflowEntityList != null && partnerapiworkflowEntityList.size() > 0){
return Boolean.TRUE;
}
} catch (NoResultException ne) {
logger.severe("some logging info.");
}
finally {
// entityManager.detach(partnerapiworkflowEntity);
}
这是一个刷新缓存的代码.
try{
entityManager.flush();
entityManager.clear();
entityManager.getEntityManagerFactory().getCache().evictAll();
//((JpaEntityManager)entityManager.getDelegate()).getServerSession().getIdentityMapAccessor().invalidateAll();
entityManager.flush();
} catch (Exception e){
throw e;
}
这是persistence.xml代码
<property name="openjpa.jdbc.DBDictionary" value="mysql"/>
<property name="openjpa.DataCache" value="true(EnableStatistics=true, CacheSize=10000, SoftReferenceSize=0, EvictionSchedule='+10')"/>
<property name="openjpa.QueryCache" value="true(EvictPolicy='timestamp')"/>
<!--<property name="openjpa.jdbc.QuerySQLCache" value="true(EnableStatistics=true)"/>-->
<property name="javax.persistence.sharedCache.mode" value="ENABLE_SELECTIVE"/>
<property name="openjpa.Instrumentation" value="jmx(Instrument='DataCache,QueryCache,QuerySQLCache')"/>
<property name="openjpa.MetaDataRepository" value="Preload=true"/>
<property name="openjpa.Log" value="SQL=Trace" />
<property name="openjpa.ConnectionFactoryProperties" value="PrintParameters=true" />
查询时总是返回值,一切正常.问题是它返回null值时开始.然后第一次存储在缓存中,然后它永远不会刷新.
我正在使用OpenJpa2和Hibernate.
解决方法:
在OpenJPA 2.2.2中首次发现了这个问题.在线查询显示,在与L2缓存(https://issues.apache.org/jira/browse/OPENJPA-2285)相关的主干上修复了一个缺陷
但是这个问题在https://issues.apache.org/jira/browse/OPENJPA-2522后期再次发现
解:
到目前为止还没有修复.但他们给出了一些绕过解决方案.
>禁用查询缓存
要禁用查询缓存(默认),请将openjpa.QueryCache属性设置为false:
<property name="openjpa.QueryCache" value="false"/>
>通过将sql查询缓存配置为false
>要指定自定义缓存类:
< property name =“openjpa.jdbc.QuerySQLCache”value =“com.mycompany.MyCustomCache”/>
>要使用非托管缓存:
< property name =“openjpa.jdbc.QuerySQLCache”value =“false”/>
要么
>要使用非托管缓存:
< property name =“openjpa.jdbc.QuerySQLCache”value =“all”/>
> Open JPA – L2 Cache Issue and Workaround
This tutorial depicts your problem same to same. Here you can get the
clear conception of occuring this error.
它提供了一个必须保留相关数据的解决方案.这样就不会出现NullPointerException.在OpenJPA无法解决问题之前,数据必须保持一致. :d
> Several mechanisms are available to the application to bypass SQL
caching for a JPQL query.
通过在OpenJPA的EntityManager SPI接口上调用以下方法,用户应用程序可以在持久化上下文的整个生命周期内禁用Prepared SQL Cache:
OpenJPAEntityManagerSPI.setQuerySQLCache(boolean)
>可以配置openjpa.jdbc.QuerySQLCache的插件属性
排除某些JPQL查询,如下所示.
< property name =“openjpa.jdbc.QuerySQLCache”value =“true(exludes ='select c from Company c; select d from Department d')”/>
永远不会缓存JPQL查询从公司c中选择c并从Department d中选择d.
查询缓存存储查询执行返回的对象ID.运行查询时,JPA会组装一个密钥,该密钥基于查询属性和启动时使用的参数,并检查缓存的查询结果.如果找到一个,则查找缓存结果中的对象ID,并返回生成的持久性对象.否则,将针对数据库启动查询,并将查询加载的对象ID放入缓存中.在完全遍历在查询启动时返回的列表之前,不会缓存对象ID列表.
L2 caching increases the memory consumption of the application,
therefore, it is important to limit the size of the L2 cache. There is
also a possibility of stale data for updated objects in a clustered
environment. Configure L2 caching for read-mostly, infrequently
modified entities. L2 caches are not recommended for frequently and
concurrently updated entities.
资源链接:
Open JPA 2.4.0 Caching Reference Guide
标签:java,spring,hibernate,performance,openjpa 来源: https://codeday.me/bug/20190623/1269421.html