我正在Hibernate 4.3.8上使用Web應用程序,它看起來像persist()
方法不會更新PersistentContext(高速緩存級別1)。下面是我的配置和單管理持久性的操作:Hibernate persist()不更新PersistentContext中的模型
Hibernate配置
<persistence-unit name="PersistenceUnit" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect"/>
<property name="hibernate.connection.driver_class" value="org.postgresql.Driver"/>
<property name="hibernate.connection.url" value="jdbc:postgresql://localhost:5432/irm"/>
<property name="hibernate.connection.username" value="nrossi"/>
<property name="hibernate.connection.password" value="nicolas"/>
<property name="hibernate.connection.pool_size" value="5"/>
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.max_fetch_depth" value="5"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
</properties>
</persistence-unit>
持久性管理
public class PersistenceManager
{
private static final Logger log = LogManager.getLogger();
private static final EntityManagerFactory emf;
private static final ThreadLocal<EntityManager> threadLocal;
static
{
emf = Persistence.createEntityManagerFactory("PersistenceUnit");
threadLocal = new ThreadLocal<EntityManager>();
}
public static EntityManager getEntityManager()
{
EntityManager em = threadLocal.get();
if (em == null)
{
em = emf.createEntityManager();
threadLocal.set(em);
}
return em;
}
public static <T>T get(Class<T> clazz, Object id)
{
return getEntityManager().find(clazz, id);
}
public static void save(Object object)
{
EntityManager em = getEntityManager();
EntityTransaction et = em.getTransaction();
et.begin();
try
{
em.persist(object);
et.commit();
}
catch (Exception e)
{
et.rollback();
throw new RuntimeException("Error saving object", e);
}
}
}
我更新模型調用PersistenceManager.save(model)
並更新記錄在數據庫上,但在此之後,當我調用PersistenceManager.get(model.id)
時,它將使用舊值從內存返回模型。它看起來像persist方法沒有更新PersistenceCache。
順便說一下,如果我在新線程(即隱身窗口)上調用PersistenceManager.get(model.id)
,它將返回更新的模型。
我試着在提交之後添加一個刷新調用em.refresh(model)
並且它正在工作,但我不確定這是否是更新上下文的正確方法。
更新信息 我編寫了一個簡單的JSP頁面來重現行爲。如果我更新的實體描述,並等待5' 和刷新頁面,則返回舊值:
<%@page import="com.identicum.framework.persistence.PersistenceManager"%>
<%@page import="com.identicum.irm.core.model.Entity"%>
<%
Entity entity = PersistenceManager.get(Entity.class, 1L);
String value = request.getParameter("entityName");
if(value != null)
{
entity.setDescription(value);
PersistenceManager.save(entity);
}
%>
<html>
<body>
Entity description: <b><%= entity.getDescription() %></b>
<br>
<br>
<form method="post">
Enter new entity description <br>
<input type="text" name="entityName"/>
<input type="submit" />
</form>
</body>
</html>
**新信息**
我的PersistenceManager這是suggestion的副本。我的應用程序是一個應用程序管理的EntityManager。我必須在每個請求的生命週期中訪問同一個EntityManager。這就是這種方法的原因。有沒有其他的方式來實現這一點?
後的所有相關代碼,包括你在哪裏加載和更新這些實體。 –
有其處理每個請求並運行下面的命令一個servlet: 1)爲了獲得模型:'PersistenceManager.get(Entity.class,ID);'和 2)更新模型: 實體實體= PersistenceManager.get(Entity.class,id); entity.setName(「B」); PersistenceManager.save(entity); PersistenceManager代碼是第一個問題。 – chupetoide
嗨艾倫,我簡化了代碼,並寫了一個簡單的jsp來重現行爲。你可以在這裏找到它(https://dl.dropboxusercontent.com/u/9319179/test.jsp)。我發現問題在幾分鐘後開始。我運行jsp並向實體發佈新描述。然後等待5分鐘,我再次運行jsp(不帶參數),然後再次看到第一個描述。 – chupetoide