使用javahibernate进行会话管理

使用javahibernate进行会话管理,java,hibernate,Java,Hibernate,我有一个基于Hibernate的平台,它由无状态servlet构建(一个用于注册用户,其余用于查询数据库) 我使用Hibernate的会话如下: Session session = HibernateUtil.getSessionFactory().getCurrentSession(); if ((null == session) || (session.isOpen() == false)) { session = HibernateUtil.getSessionFactory().op

我有一个基于Hibernate的平台,它由无状态servlet构建(一个用于注册用户,其余用于查询数据库)

我使用Hibernate的会话如下:

Session session = HibernateUtil.getSessionFactory().getCurrentSession();
if ((null == session) || (session.isOpen() == false)) {
  session = HibernateUtil.getSessionFactory().openSession();
}
目前,为了避免调用
openSession()
(如果可能,尝试使用打开的会话),我没有在servlet结束时关闭会话

最佳做法是什么?我应该什么时候结束这些会议

你能举个例子吗


提前谢谢

在大多数情况下,最佳做法是每次请求会话。也就是说,在开始处理请求时打开一个会话,然后在结束时关闭它。例如,您可以在Servlet
过滤器中执行此操作

为整个应用程序使用一个会话是不好的,因为它会在一级缓存中积累大量实体,这是内存泄漏。当多个客户端同时使用它时,它也可能产生不确定的结果


但是,您的代码并不是对整个应用程序使用一个会话,而是使用“当前会话”概念,它打开一个会话并将其存储在上下文中(例如
ThreadLocal
)。但如果你不关闭它,它将永远留在那里。另外,它将导致与上述相同的问题,因为线程在web应用程序中被重用,而新请求将在某个时候获得一个旧的、未关闭的会话。

最好为每个请求打开一个新会话,并在处理完请求后关闭会话。像

Session session = HibernateUtil.getSessionFactory().openSession();
而不是

Session session = HibernateUtil.getSessionFactory().getCurrentSession();

如果使用getCurrentSession()方法,则tansaction.commit()/rollback()会关闭连接

管理hibernate会话的最佳方法是为每个请求打开一个新会话。 这完全取决于您如何获得会话

  • 如果使用sessionFactory.getCurrentSession(),将获得 绑定到事务生命周期的“当前会话” 并将在交易结束时自动刷新和关闭 结束(提交或回滚)
  • 如果决定使用sessionFactory.openSession(),则必须 自己管理会话,并“手动”刷新和关闭会话

我最好推荐您使用spring框架。因为在spring中,您可以在方法级别使用
@Transactional
,而会话将由transaction manager使用
AOP
自动创建和关闭(除非您使用的是视图拦截器中的任何打开的会话),后者由框架内部处理

@Autowired
EntityManager em;

@Transactinal
void save(User user){
   em.persist(user);
}

仅此而已。spring很有趣:D

“为每个请求创建新会话”是反模式的。我同意为整个应用程序创建一个会话是一个坏主意,但是为每个请求创建当前会话而不是打开-关闭会话如何,特别是当您同时应用spring和hibernate时?
@Autowired
EntityManager em;

@Transactinal
void save(User user){
   em.persist(user);
}