将Java EE资源注入动态加载的类中

时间:2016-03-26 18:37:49

标签: java-ee cdi wildfly tomee tomee-7

这是一个由Java EE应用程序在运行时生成/加载的类(@Default Bar bean由同一个应用程序提供):

public class Foo {

    @PersistenceContext private EntityManager em;
    @Resource private UserTransaction tx;
    @EJB private MyEJB ejb;
    @Inject Bar bar;

    public Foo() {
    }

    @PostConstruct
    public void postConstruct () { ... }

    public void businessMethod() { ... }

}

以下是它的实例化方式:

    import javax.enterprise.inject.spi.Unmanaged;
    ...

    @Inject private BeanManager bm;
    ...

    Class clazz = loadClazz();

    Unmanaged unmanaged = new Unmanaged(bm, clazz);

    Object obj = unmanaged.newInstance()
            .produce()
            .inject()
            .postConstruct()
            .get();

使用JBoss / WildFly,所有字段都被正确注入,包括EntityManager,EJB,UserTransaction等。

使用TomEE和GlassFish,将忽略Java EE资源,只会注入bar字段。

  1. 这应该被视为TomEE和GlassFish中的错误,还是仅仅是JavaEE / CDI规范中的白点,在应用服务器中实现的方式不同?它绝对不是纯粹的CDI问题,因为GlassFish和WildFly都使用相同的CDI实现,即JBoss Weld;
  2. 如何通过TomEE和GlassFish实现上述目标?便携式解决方案是首选,但一些依赖服务器的代码是可以的(我担心这种问题不可避免)。
  3. 总体目标是提供全方位的CDI注入(简单@Inject以及Java EE资源,如@PersistenceContext@Resource@EJB等。动态代码。我的第一次尝试是生成一个即时的类,它将包含带注释的字段+动态业务逻辑(是的,它可以工作,但仅限于WildFly)。一般来说,我有一组动态注入定义,如下所示:

    @Annotation(param = "value") @Qualifier1 @Qualifier2 ... Type name;
    

    其中AnnotationInjectPersistenceContextResourceEJB等之一,我希望获得一个已经注入的实例如果这是在CDI托管bean中。因此,假设采用注入元数据并返回相应实例的假设方法是可接受的。

1 个答案:

答案 0 :(得分:0)

您是否尝试过declaring resources via producer fields

这样做,您可@Inject EntityManagerUserTransaction等,而无需借助CDI之前的注释。

由于通过@Inject注入CDI似乎适用于所有环境,因此这可能是一个可行的解决方案。