我正在使用jboss 5.1.0.GA (build: SVNTag=JBoss_5_1_0_GA date=200905221634)
.并且需要获取豆子的业务接口。这对于事务管理是必需的。所以我有:
@Local
public interface MyBeanInterface {
void transactionalMethod();
}
@Stateless
public class MyBean implements MyBeanInterface {
@Resource
private SessionContext context;
private int aState;
public void someMethod() {
aState = 42;
context.getBusinessObject(MyBeanInterface.class).transactionalMethod();
}
@TransactionAttribute(TransactionAttributeType.NOT_SUPPORTED)
public void transactionalMethod() {
System.out.println(aState); // 0!!!!!
}
}
由于某种原因,我没有得到相同的豆子,但创建了新豆子。这是灾难性的,因为transactionalMethod
需要状态变量值才能正确执行。
我做错了什么,或者那是jboss的错误?顺便说一下,有一个错误会影响通过 bean 类获取业务对象的能力:https://issues.jboss.org/browse/EJBTHREE-2126。但是不确定它是否与我的问题有关。
最好的解决方案是这样的:
@Stateless
public class MyBean implements MyBeanInterface {
@Resource private TransactionManager tm;
private int aState;
public void someMethod() {
aState = 42;
Transaction transaction = tm.suspend();
transactionalMethod();
tm.resume(transaction);
}
@TransactionAttribute(TransactionAttributeType.NOT_SUPPORTED)
public void transactionalMethod() {
System.out.println(aState); // 0!!!!!
}
}
当您从同一位置调用已发布的接口方法时,通过 ejb 上下文传递,资源为:
- 如果@Stateless,则会创建一个新实例。
- 如果@Stateful,则为第一个呼叫创建一个新会话,则其他呼叫与@Singleton相同。
- 如果@Singleton,则调用方等待资源被释放,如果它调用自身,则会创建死锁。如果该方法带有 @Read 注释,则调用 yourself 不会创建任何死锁。
我没有时间看看语法是否完美,但你可以试试:
InitialContext jndiContext = new InitialContext();
Object ref = jndiContext.lookup("projname/MyBeanInterface/local");
MyBeanInterfaceLocal m = (MyBeanInterfaceLocal) ref;
但是,我看到您有一个SessionContext字段,因此也许对您来说,代码应该有点不同。也许会是:
Object ref = SessionContext.lookup("projname/MyBeanInterface/local");
MyBeanInterfaceLocal m = (MyBeanInterfaceLocal) ref;
让我知道这是否有帮助!