通过参考T1和T2,哪种方法在创建休眠事务时是正确的做法?我怀疑选择其中之一。 我的问题是在什么情况下应该像T1或T2那样编码。
T1
try{
currentSession.beginTransaction();
// assume assume this method is a hql select query
Person person=personService.findPerson(personId);
// complex rules that will affect performance
Health health=healthService.calculateComplexBizRules(personId);
person.setHealth(health);
currentSession.commitTransaction();
}catch (Exception e) {
rollBackTransaction();
e.printStackTrace();
throw e;
}
T2
try{
currentSession.beginTransaction();
// assume this method is a hql select query
Person person=personService.findPerson(personId);
currentSession.commitTransaction();
// complex rules that will affect performance
Health health=healthService.calculateComplexBizRules(personId);
currentSession.beginTransaction();
currentSession.persist(health);
Person person=currentSession.merge(person);
person.setHealth(health);
currentSession.commitTransaction();
}catch (Exception e) {
rollBackTransaction();
e.printStackTrace();
throw e;
}
答案 0 :(得分:1)
T1是全有还是全无。
因此,如果healthSerivce引发异常,则可以回滚(或根据应用程序框架自动回滚)事务。
对于T2(取决于基础数据库),使用find进行的事务将不会在数据库级别上创建事务(例如,使用Oracle)。因此,第一笔交易还是没用的。
如果您使用的是Jakarta EE(以前的J2EE / Java EE)或Spring这样的应用程序框架,则将具有声明性事务边界,很有可能看起来像T1。
如果您的负载非常大,则可以选择T2来使事务短。
总结:这取决于您的用例
答案 1 :(得分:0)
1)如果使用乐观锁定,则在两种情况下都将在复杂操作之前检索Person
。这意味着,提交后,如果数据库的版本高于最初检索的版本,您将获得OptimisticLockException
,您需要从中进行恢复(通常是在合并后重复操作)。 T1
和T2
选项就是这种情况。您需要根据对系统在此处的行为的研究来决定选择哪一个,并做出适当的判断(T2打开和关闭第二个事务,这会增加总执行时间,并且在这种情况下不会增加任何额外的好处)。
2)如果您需要使用悲观锁定,这意味着一旦完成复杂操作,就将数据库上的行物理锁定,那么您需要进行T1。如果您的Person
每秒可能被查询多次,那么这可能就是瓶颈。