本文介绍了如何告诉CDI容器“激活”?一个豆?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一些注射课程:

Suppose I have some class with injections:

class MyBean {

    @Inject
    Helper helper;

    // all sorts of data
}

这个class是以CDI容器不知道的方式创建的,如反射,序列化或 new 。在这种情况下,助手 null ,因为CDI没有为我们初始化它。

and this class was created in a way the CDI container is not aware of it like reflection, serialization or new. In this case the helper is null because the CDI did not initialize it for us.

有没有办法告诉CDI激活豆子或至少注射它?例如,好像它是用 Instance< MyBean> #get 创建的?

Is there a way to tell CDI to "activate" the bean or at least its injection? e.g., as if it was created with Instance<MyBean>#get?

现在我有一个黑客在哪里我执行以下操作:

Right now I have a hack where I do the following:

class SomeClass {

    @Inject
    Instance<MyBean> beanCreator;

    void activateBean() {
        MyBean mybean = ... // reflection/serialization/new
        MyBean realBean = beanCreator.get();
        Helper proxy = realBean.getHelper();
        mybean.setHelper(proxy);
        beanCreator.destroy(realBean);
    }
}

这看起来很糟糕但它适用于我测试的所有内容。它只显示了我想要的最终结果。

This looks pretty bad but it works for everything I tested. It just shows what the end result is that I want.

如果重要的话使用Wildfly 10.1。

Using Wildfly 10.1 if it matters.

推荐答案

首先,你使用 MyBean 的方式不是CDI方式;事实上,你操作所谓的非上下文对象。您正在做的是采用非CDI管理对象并要求CDI解决注入点。这是非常不寻常的,因为你处理生命周期的一部分(创建/销毁),同时要求CDI完成其余的工作。

First of all, the way you use MyBean is not a CDI way; in fact you operate on so called non-contextual object. What you are doing is taking a non-CDI managed object and asking CDI to resolve injection points. This is quite unusual, as you handle part of the lifecycle (creation/destruction), while asking CDI to do the rest.

在你的情况下, MyBean 类需要成为,这就是你应该开始寻找的方式。为了触发注射你需要做这样的事情(在创建 MyBean 期间):

In your case, the MyBean class needs to become InjectionTarget, and that is the way you should start looking. In order to trigger injection you will want to do something like this (during creation of MyBean):

// Create an injection target from your given class
InjectionTarget<MyBean> it = beanManager.getInjectionTargetFactory(beanManager.createAnnotatedType(MyBean.class))
                .createInjectionTarget(null);
CreationalContext<MyBean> ctx = beanManager.createCreationalContext(null);
MyBean instance = new MyBean();
it.postConstruct(instance); // invoke @PostContruct
it.inject(instance, ctx); // trigger actual injection on the instance

请注意这种方法通常很笨拙(因为很难让它工作和维护)并且最好将 MyBean 转换为真正的CDI bean,并将整个生命周期管理留给CDI。但是,为此,您的问题没有提供足够的信息。

Please note that this approach is usually clumsy (as in hard to make it work and maintain) and it might be better to instead turn your MyBean into a true CDI bean and leaving whole lifecycle management to CDI. For that, however, your question doesn't provide enough information.

这篇关于如何告诉CDI容器“激活”?一个豆?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-23 00:51