java 休眠保存和获取使用相同的会话,相同的事务

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/7496496/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-30 20:13:52  来源:igfitidea点击:

hibernate save and get using same session ,same transaction

javahibernatespringtransactions

提问by cometta

I have a scenario service layer is transactional, where i can only commit after done trandaction. i simplified it into like below.

我有一个场景服务层是事务性的,我只能在完成交易后提交。我将其简化为如下所示。

begin transaction

for(loop){

getHibernateTemplate().save(object);


getHibernateTemplate().get(object_by_key); //cannot get object by object_by_key because "object" is not commit into database until entire for(loop) completed. 

}

end transaction. commit();

i try to put getHibernateTemplate().flush(), after save() and able to see "insert" in show_sql. but the record is not showing inside database. how to force write to database after each save() rather than wait for commit like above ?

我尝试在 save() 之后放置 getHibernateTemplate().flush() 并且能够在 show_sql 中看到“插入”。但记录未显示在数据库内。如何在每次 save() 后强制写入数据库而不是像上面那样等待提交?

采纳答案by gkamal

getHibernateTemplate().flush() is the method to force hibernate to write to the database (send insert & update queries). This is done within a transaction so it is not visible to other transactions (querying from a SQL client) till the transaction is committed.

getHibernateTemplate().flush() 是强制休眠写入数据库的方法(发送插入和更新查询)。这是在事务中完成的,因此在提交事务之前,它对其他事务(从 SQL 客户端查询)不可见。

If the insert query is showing up in the log then it has been sent to the database. If you want to test that the record was inserted correctly - you can either do a getHibernateTemplate().clear() (which will remove all the cached data) and then do a getHibernateTemplate.get() (which will query from the dataSource). Or the other approach to test is to use the jdbcTemplate (with the same database) to query and check.

如果插入查询显示在日志中,则它已发送到数据库。如果您想测试记录是否正确插入 - 您可以执行 getHibernateTemplate().clear() (这将删除所有缓存的数据),然后执行 getHibernateTemplate.get() (它将从数据源查询) . 或者另一种测试方法是使用jdbcTemplate(同一个数据库)来查询和检查。

If the SQL client tool you are using allows you to specify the Isolation level - starting the SQL client session in isolation read_uncommited - would allow you to see the changes done even before the transaction is commited.

如果您使用的 SQL 客户端工具允许您指定隔离级别 - 以隔离方式启动 SQL 客户端会话 read_uncommited - 将允许您甚至在提交事务之前查看所做的更改。

回答by Max Zerbini

Why do you need to get the object by key? You already have the object! If really you need the object key (for print it?) you can use a new transaction for each save operation, putting the transaction beginand commitin the loop.

为什么需要通过key来获取对象?你已经有了对象!如果您真的需要对象键(用于打印?),您可以为每个保存操作使用一个新事务,将transaction beginandcommit放入循环中。

回答by James DW

Does getHibernateTemplate() return the same template each time? Or if not a template based on a common session. You might be better off saving the template to a local variable and reusing it, rather than calling getHibernateTemplate() each time.

getHibernateTemplate() 是否每次都返回相同的模板?或者如果不是基于公共会话的模板。您最好将模板保存到局部变量并重用它,而不是每次都调用 getHibernateTemplate()。

begin transaction

template = getHibernateTemplate();

for(loop){

template.save(object);


template.get(object_by_key); //cannot get object by object_by_key because "object" is not commit into database until entire for(loop) completed. 

}

end transaction. commit();

I think your problem might be because you are using a different session for the save and get calls. If they are made to the same session you should see the behaviour you want.

我认为您的问题可能是因为您使用不同的会话进行保存和获取调用。如果它们是针对同一个会话进行的,您应该会看到您想要的行为。

回答by BrownFurSeal

As I know you can't do it at all. It doesn't work. It is not possible to retrieve saved object in the same transaction. I think it is because the session is the first-level cache and Hibernate can obtain a new object only when the another transaction that creates that object commited.

据我所知,你根本做不到。它不起作用。不可能在同一事务中检索保存的对象。我认为是因为会话是一级缓存,只有当创建该对象的另一个事务提交时,Hibernate 才能获取新对象。