Datanucleus:从 @Transactional 转向非事务性
我正在使用 Datanucleus、JDO 和 Spring 与 Aspect-J 交织的声明式 @Transactional
管理。
但是,当“普通”方法从 @Transactional 方法获取持久对象时,该对象的状态将变为瞬态(持久管理器似乎已被删除)并且该对象不再是持久的。
示例:
public class Example {
public void test() throws Exception {
Login l = getLogin();
JDOHelper.getObjectState(l); // transient instead of persistent
l.getSomeOtherPersistentObj().doStuff(); // NullpointerException :(
}
@Transactional
private Login getLogin() {
// do transactional stuff here
// ..
return dao.find(Login.class, 1);
}
}
这是为什么?如何在不需要事务的地方添加 @Transactional
的情况下修复它?以下确实(显然)有效,因此这表明可以建立事务性连接和非事务性连接:
- @Transactional 方法调用 @Transactional 方法
- @Transactional 方法调用普通方法
- 普通方法调用普通方法
如果我调用 dao.refresh(l)
,我得到:“ID 为“”的对象由不同的对象管理器管理”,所以 Spring 可能正在使用与 DAO 不同的持久性管理器,是这样吗?这 原因?
这是我的弹簧配置(可能相关):
<bean id="pmf" class="org.datanucleus.api.jdo.JDOPersistenceManagerFactory" destroy-method="close">
<property name="connectionDriverName" value="com.mysql.jdbc.Driver"/>
...
<constructor-arg>
<map>
<entry key="datanucleus.autoCreateSchema" value="true" />
</map>
</constructor-arg>
</bean>
<bean id="myPmfProxy" class="org.springframework.orm.jdo.TransactionAwarePersistenceManagerFactoryProxy">
<property name="targetPersistenceManagerFactory" ref="pmf" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jdo.JdoTransactionManager">
<property name="persistenceManagerFactory" ref="myPmfProxy" />
</bean>
<bean id="JDODao" class="sw.JDODao">
<property name="persistenceManagerFactory" ref="myPmfProxy" />
</bean>
I am using Datanucleus, JDO and Spring's declarative @Transactional
management woven with Aspect-J.
But when a 'normal' method gets a persistent object from a @Transactional
method, the object's state will become transient (the persistence manager seems to be removed) and the object is no longer persistent.
Example:
public class Example {
public void test() throws Exception {
Login l = getLogin();
JDOHelper.getObjectState(l); // transient instead of persistent
l.getSomeOtherPersistentObj().doStuff(); // NullpointerException :(
}
@Transactional
private Login getLogin() {
// do transactional stuff here
// ..
return dao.find(Login.class, 1);
}
}
Why is this and how can I fix it without adding @Transactional
in places where transactions are not needed? The following does (obviously) work so this indicates that a transactional as well as a non-transactional connection can be made:
- A @Transactional method calls a @Transactional method
- A @Transactional method calls a normal method
- A normal method calls a normal method
If I call dao.refresh(l)
, I get: 'Object with id "" is managed by a different Object Manager', so maybe Spring is working on a different persistence manager than the DAO, is this the cause?
Here's my spring configuration (it might be relevant):
<bean id="pmf" class="org.datanucleus.api.jdo.JDOPersistenceManagerFactory" destroy-method="close">
<property name="connectionDriverName" value="com.mysql.jdbc.Driver"/>
...
<constructor-arg>
<map>
<entry key="datanucleus.autoCreateSchema" value="true" />
</map>
</constructor-arg>
</bean>
<bean id="myPmfProxy" class="org.springframework.orm.jdo.TransactionAwarePersistenceManagerFactoryProxy">
<property name="targetPersistenceManagerFactory" ref="pmf" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jdo.JdoTransactionManager">
<property name="persistenceManagerFactory" ref="myPmfProxy" />
</bean>
<bean id="JDODao" class="sw.JDODao">
<property name="persistenceManagerFactory" ref="myPmfProxy" />
</bean>
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
事实证明,我的对象需要可拆卸才能做到这一点。
我将
(detachable="true")
添加到我的@PersistenceCapable
注释中,并设置以下 datanucleus 选项:It turned out that my objects need to be detachable to do this.
Iv'e added
(detachable="true")
to my@PersistenceCapable
annotations and set the following datanucleus options: