我遇到的问题是JPA将旧数据保存在缓存中并尝试了我能找到的解决方案,但它一直在弹出!
无论如何,我最初重用一个Entity Manager实例来提高效率。当我第一次遇到上述问题时,我更改了我的代码,以便每个事务生成一个新的实体管理器:
/** This method is called every time a transaction is made. */
public static EntityManager createFreshEntityManager() {
try {
return Persistence.createEntityManagerFactory(puName)
.createEntityManager();
}
catch (Exception e) {
logStuff(e);
return null;
}
}
但是,这并不能解决问题。
当我使用JDBC截断表并重置主键时,我经常注意到某些新创建的对象具有旧的变量值。我有一个怀疑是重置主键可能是罪魁祸首,但话说回来,我已经为每个事务都有一个新的实体管理器,所以这根本不重要。
我非常有信心这不是我的代码的问题,因为数据库实体永远不会存储在我的应用程序之外的功能范围内,并且在需要时总是直接从数据库中查询。
我也读过有关使用EntityManager.clear()的内容,但我不想做那些残酷的事情,因为它会搞乱多线程程序。
我曾经想过通过一次获取所有对象然后手动删除它们来使用JPA而不是JDBC来进行TRUNCATE,但这只是效率低下......但是再次,它不会成为瓶颈。不确定这是否会对w.r.t产生影响。尽管如此使用JDBC。
答案 0 :(得分:2)
我认为没有理由为每个事务创建一个新的EntityManager。
您应该可以使用EntityManager注入@PersistenceContext。
它可能看起来像这样:
@Stateless
class SomeSessionBean implements SomeSessionBeanLocal {
@PersistenceContext(unitName = "somePuName")
private EntityManager em;
public Customer findCustomerById(Long someId) {
return em.find(Customer.class, someId);
}
}
使用注释进行依赖注入是EJB 3最重要的事情之一!
问题的可能来源:
如果在JavaEE Web应用程序运行时修改数据库中的值,则EJB不可能立即检测到这些更改。你的持久层可能正在使用缓存。
您可能希望在进行数据库更改“external ”后重新启动您的webapp。