Java 单例EJB中的系统异常

Java 单例EJB中的系统异常,java,jakarta-ee,singleton,ejb,Java,Jakarta Ee,Singleton,Ejb,我正在阅读EJB规范,从我的观点来看,我被一个矛盾弄糊涂了,特别是在单例Bean的生命周期回调方法中抛出系统异常时,容器的行为方式 第12.3.1节: 任何生命周期拦截器回调引发的运行时异常 方法导致bean实例及其拦截器被丢弃 在拦截器链解绑和任何相关拦截器后 实例被丢弃(单例bean除外) 第4.8.4节: 在单例初始化期间发生的错误被认为是致命的 并且必须导致丢弃单例实例。可能的 初始化错误包括注入失败、系统异常 从后构造方法引发,或后构造失败 方法容器管理的事务成功提交 与其他组件类型的

我正在阅读
EJB规范
,从我的观点来看,我被一个矛盾弄糊涂了,特别是在
单例Bean的生命周期回调方法中抛出
系统异常
时,
容器
的行为方式

第12.3.1节:

任何生命周期拦截器回调引发的运行时异常 方法导致bean实例及其拦截器被丢弃 在拦截器链解绑和任何相关拦截器后 实例被丢弃(单例bean除外)

第4.8.4节:

在单例初始化期间发生的错误被认为是致命的 并且必须导致丢弃单例实例。可能的 初始化错误包括注入失败、系统异常 从后构造方法引发,或后构造失败 方法容器管理的事务成功提交

与其他组件类型的实例不同,引发了系统异常 来自业务方法或单个实例的回调不会导致 销毁单例实例

那么,根据第4.8.4节,什么是正确的?如果在
@PostConstruct
方法或
拦截器
@PostConstruct
方法中抛出
系统异常
Bean是否已丢弃?我尝试过抛出一个
EJBException
,结果是bean初始化失败


更令人惊讶的是,当从
单例Bean
业务方法抛出
EJBException
时,客户端收到了
异常
,没有进一步执行其他方法。我可以假设Bean实例已被丢弃吗?根据规范,不应该导致
Bean实例的破坏。在这两种情况下,什么是正确的

我要的是代码,因为这可能是供应商的错误。正如您所读到的,如果在@postcontract time有一个EjbException,则不会构建单例。在此之后,单例方法可以抛出任何类型的异常(已检查或未检查),并且实例应该仍在运行

拦截器生命周期附加到单例生命周期,因此,如果拦截器无法执行其@postcontuct,将不会创建单例


要记住的另一件事是:如果EJB(@Stateless或@Stateful)抛出一个EjbException(或其拦截器),实例会自动被丢弃,因此,规范中有一条注释说:
[58]除了单例。请参阅第4.8.4节

请提供一些您正在测试的代码,希望有关于您期望的内容以及您正在使用的内容的注释(仅用于测试目的)?我可以发布一些代码(一旦我再次访问我的Java EE环境),但主题非常理论化。我想知道单例Bean中@PostConstruct方法中的系统异常是否会导致容器对Bean的污染。在我的问题中引用的两个“引用”中描述了这种情况,从我的观点来看,它们是相互冲突的。你在回答中所说的正是我过去相信的,但在阅读了更多的规范章节后,我开始怀疑。可能生命周期回调方法中的系统异常对单例的非破坏不适用于'PostConstruct'方法,因此@PreDestroy。如果
@PostConstruct
抛出运行时异常,则不会创建单例。而且,
@postcontract
在ejb的生命周期中只运行一次。