且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

getCurrentSession在web中休眠

更新时间:2022-10-30 20:20:20


在步骤1和步骤3会是同一个会话吗?

它们应该是相同的,这是 getCurrentSession( ),只要工作单元尚未完成(即事务已提交),您将获得绑定到该线程的 Session 或回滚)。使用Hibernate的Java持久化如下所示(p.481):


所有数据访问代码在全局共享
SessionFactory 上调用 getCurrentSession()可以访问相同的当前 Session - 如果它在
同一线程中调用。当 Transaction 被提交(或回滚)时,工作单元完成。如果您提交或回滚事务,Hibernate也会刷新并关闭当前的 Session 及其持久化上下文。这意味着在提交或回滚之后调用 getCurrentSession()会产生一个新的 Session 和一个新的持久化上下文。


您可能还想阅读 Session#beginTransaction() 说。
$ b


如果问题1的答案是肯定的,那么它将如何处理步骤4中的提交。理想情况下,它应该关闭那里的会话本身并应该在第5步出错。

第4步应该不是问题, Session 将被刷新, Transaction 将被提交并且 Session 关闭。但我预计第5步将失败 TransactionException (这是我的赌注)。但让我引用 Transaction
$ b


事务与Session相关联,并且通常通过调用来实例化 Session.beginTransaction()。单个会话可能跨越多个事务,因为会话的概念(应用程序和数据存储之间的对话)比事务概念的粒度更粗。但是,它的目的是在任何时间最多只有一个与特定会话相关的未提交的交易。





I am writing a web based application with hibernate and jsp/servlet. I have read about the sessionFactory.getCurrentSession and sessionFactory.openSession methods. I know the basic difference between them (using getCurrentSession you don't have to close the connection and when you commit the transaction, your session will automatically close). According to the my understanding, we should opt for getCurrentSession and do it through session-per-request.

Let's consider the following scenario:

  1. Method A calls getCurrentSession and got the current session
  2. In Method A, a transaction is started using the session from step 1
  3. Method A calls Method B, which also has getCurrentSession and starts a transaction
  4. Method B commits its transaction
  5. Control returns to method A and it also commits the transaction

Now my questions are

  1. Will the session found in step 1 and step 3 will be the same session?
  2. If the answer for the question 1 is yes, then how would it handle the commit in step 4? Ideally it should close the session there itself and should throw an exception at step 5.
  3. If the answer for the question 1 is no, then how do you handle such a scenario?

Will the session found in step 1 and step 3 will be the same session?

They should be the same, that's somehow part of the contract of getCurrentSession() and you'll get the Session bound to the thread as long as the unit of work has not been completed (i.e. a transaction has been committed or rolled back). Java Persistence with Hibernate puts it like this (p.481):

All the data-access code that calls getCurrentSession() on the global shared SessionFactory gets access to the same current Session — if it’s called in the same thread. The unit of work completes when the Transaction is committed (or rolled back). Hibernate also flushes and closes the current Session and its persistence context if you commit or roll back the transaction. The implication here is that a call to getCurrentSession() after commit or rollback produces a new Session and a fresh persistence context.

And you might also want to read what the javadoc of Session#beginTransaction() says.

If the answer for the question 1 is yes, then how would it handle the commit in step 4. Ideally it should close the session there itself and should give error at step 5.

Step 4 shouldn't be a problem, the Session will be flushed, the Transaction will be committed and the Session closed. But I expect step 5 to fail wih aTransactionException (that's my bet). But let me quote the javadoc of Transaction:

A transaction is associated with a Session and is usually instantiated by a call to Session.beginTransaction(). A single session might span multiple transactions since the notion of a session (a conversation between the application and the datastore) is of coarser granularity than the notion of a transaction. However, it is intended that there be at most one uncommitted Transaction associated with a particular Session at any time.

As underlined above, we are discussing around something that shouldn't happen (i.e. a design problem).