2015-07-03 53 views
0

我正在研究EJB查找的洞察力,并试图了解容器和池如何工作。我创建了一些测试应用程序,我将解释每一个应用程序。EJB内部查找:构造函数,@PostConstruct

先执行:查找内部构造函数类的构造函数(糟糕的做法)内进行

@Stateless 
    public class EjbTest { 

    protected EjbInjectedLocal  ejbInjected; 

    public EjbTest() { 
      InitialContext ic = new InitialContext(); 
      ejbInjected = (EjbInjectedLocal)ic.lookup("java:comp/env/ejb/EjbInjected"); 
      ic.close(); 
    } 

    public void test() { 
     ejbInjected.callSomeMethod(); 
     return; 
    } 

} 

注射,但一切正常。构造函数检索EJB的代理。当我调用方法test()时,它会正确执行。

第二实施:查找内部@PostConstruct

@Stateless 
public class EjbTest { 

    protected EjbInjectedLocal  ejbInjected; 

    public EjbTest() { 
    } 

    @PostConstruct 
    public start() { 
      InitialContext ic = new InitialContext(); 
      ejbInjected = (EjbInjectedLocal)ic.lookup("java:comp/env/ejb/EjbInjected"); 
      ic.close(); 
    } 

    public void test() { 
     ejbInjected.callSomeMethod(); 
     return; 
    } 

} 

如在现有例子中,查找工作正常,以及所述方法测试。

三实现:构造函数和函数执行

@Stateless 
public class EjbTest { 

    protected EjbInjectedLocal  ejbInjected; 

    public EjbTest() { 
      InitialContext ic = new InitialContext(); 
      ejbInjected = (EjbInjectedLocal)ic.lookup("java:comp/env/ejb/EjbInjected"); 
      ejbInjected.callSomeMethod(); 
      ic.close(); 
    } 

} 

内查找使用这种实现,查找工作正常,但功能停止/冻结线程,因为容器尚未准备好来无回代理实现,但是整个EJB和函数都无法执行。

当构造函数被调用时,bean尚未被初始化并且没有依赖被注入?只有代理被返回,但它尚不可用,无法从池中检索整个EJB?

回答

2

EJB specification(4.3.10.2):

由于无状态会话bean实例通常汇集,创建方法的客户端调用时 不必为容器的调用任何 直接关系对无状态会话bean实例的PostConstruct/ejbCreate方法的 。

这是特定于容器的行为,规范将其作为实现者进行创新的区域开放。实现甚至不要求使用Bean池,并成为可用的任何延迟加载行为的确切顺序豆到容器中,如为他们提供他们的用户的配置,例如:

http://docs.jboss.org/ejb3/docs/reference/1.0.7/html/SessionBean_and_MDB_configuration.html

关于实例化过程中的调用序列,规范(第4.3.10节)说:

容器按如下方式创建会话bean的实例。首先, 容器调用bean类的newInstance方法来创建一个 新的会话bean实例。其次,容器执行任何 依赖注入,如bean 类上的元数据注释或部署描述符所指定的。这包括Bean的 SessionContext(如果适用)。第三,容器为这个bean调用 PostConstruct生命周期回调拦截器方法,如果是 任何。如果会话bean是通过EJB 2.1客户端视图API调用的 ,则下面描述的附加步骤适用。

尤其是,任何依赖注入字段(即使用EJB注释)在此时都将为空。通过使用InitialContext你已经绕过了这个约束,这是意外行为的原因。

根据您描述的行为,听起来好像您的容器正在构建bean,因此EjbInjectedLocal bean在您尝试调用它的位置不可用。我很惊讶它僵局,但并不惊讶它没有奏效。在其他容器上尝试相同的实验并查看是否得到相同的结果会很有趣。

0

只返回代理,但它尚不可用,无法从池中检索整个EJB?

这是正确的。你只是在这里陷入僵局。

+0

调用方法EjbTest()时,EJB代理可用,但在调用@PostConstruct方法(类构造函数完成之后)之前,EjbTest EJB尚未准备好。但是第三个例子很少有工作正常..这只是一个时间任务完成的问题? – StarsSky