2012-02-17 38 views
2

我有一个标准Spring Roo(1.2.0.RC1)项目,带有标准域对象。在我的主线程(域控制器)中,我可以使用查找器创建由数据库支持的域对象(我使用Hibernate/MySQL)的实例,更改一些属性并通过调用.persist()将这些更改持久保存到数据库中在要保存的实例上。.persist()在Spring Roo中无法在新线程中工作

如果我这整个逻辑移动到一个Runnable,并在一个新的线程(由ScheduledThreadPoolExecutor.scheduleAtFixedRate()调用),我仍然可以正常创建使用取景器,但改变一些属性的域对象的情况下,执行它,对要保存的对象调用.persist()对DB没有影响。我在控制台日志中看不到任何内容(在STS内部运行)。我不知道Roo是否创建了任何其他日志文件,这可能会给我提供更多关于可能发生的线索的线索。有没有人遇到过上述问题?有谁知道如何在STS控制台中获得更详细的日志记录(例如Hibernate查询日志记录)吗?

+0

显示我们的代码。并且请注意,Hibernate Session是单线程对象,并且事务上下文依赖于ThreadLocal变量。 – 2012-02-17 22:41:19

+0

将休眠属性show-sql添加到persistence.xml以获取更多信息 – Ilya 2012-02-17 22:55:04

+0

是的,Hibernate会话通常存储为ThreadLocal变量 - 因此您在新线程中创建的对象没有Hibernate会话。 – GreyBeardedGeek 2012-02-22 02:07:28

回答

0

它与交易有关。 Hibernate或JTA中的默认值是使用绑定到线程的本地事务。真的,你不应该尝试跨线程共享事务。无论你在线程之间共享什么对象(休眠会话?),我敢打赌他们实际上并不是线程安全的。

我会尽量简化您的代码,而不是在多个线程中处理更新。如果您必须使用多个线程,则他们必须各自拥有自己的事务。

很可能,您只需要为每个线程创建一个新的事务。但这就是为什么你可以从你的线程中选择数据,但你不能坚持。这听起来像你的线程内的交易没有被关闭。

相关问题