簡體   English   中英

如何使用CDI注入第三方實例化的對象

[英]How to use CDI to inject into an object instantiated by 3rd party

我有一個由第三方代碼實例化的類(它使用反射來創建對象。)我提供了他們的接口的實現,他們創建了對象。 在我的實現中,我想使用CDI注入執行邏輯的服務。 這樣做的正確方法是什么?

public interface ThirdPartyInterface {
    public void DoSomething();
}

public class InjectedService {
    public void DoSomeLogic() { ... }
}

public class MyImplementation implements ThirdPartyInterface {
    @Inject InjectedService service;

    @Override
    public void DoSomething() {
        service.DoSomeLogic();
    }
}

我原本以為這可以通過CDI的魔力,但發現我的服務對象為null。

到目前為止,我唯一想到的就是在構造函數中手動注入服務

 public MyImplementation() {
     CDI<Object> cdi = CDI.current();
     service = cdi.select(InjectedService.class).get();
 }

這是獲取實例的正確/唯一/最佳方式嗎? 我正在使用Weld來實現我的CDI。

我也發現這在構造函數中起作用:

    public MyImplementation() {
        CDI<Object> cdi = CDI.current();
        BeanManager bm = cdi.getBeanManager();
        AnnotatedType<MyImplementation> myType = bm.createAnnotatedType(MyImplementation.class);
        Set<Bean<?>> beans = bm.getBeans(MyImplementation.class);
        Bean<?> bean = bm.resolve(beans);
        @SuppressWarnings("unchecked")
        CreationalContext<MyImplementation> cc = (CreationalContext<MyImplementation>)bm.createCreationalContext(bean);
        bm.createInjectionTarget(myType).inject(this, cc);
   }

只要有人手動創建對象,默認情況下,CDI就不會向其中注入任何內容。

您使用構造函數注入的方法可能會起作用,除非您進入EAR並且CDI.current()可能無法執行您期望的操作。

有一種方法可以將CDI注入到手動創建的對象中 - 第三方必須采取這一步驟才能使其工作。 您需要BeanManager和要注入的實例:

        BeanManager beanManager = ...; // get hold of bean manager, can be injected
        CreationalContext<Object> ctx = beanManager.createCreationalContext(null);
        @SuppressWarnings("unchecked")
        InjectionTarget<MyImplementation> injectionTarget = (InjectionTarget<MyImplementation>) beanManager
            .getInjectionTargetFactory(beanManager.createAnnotatedType(myImplementationInstance.getClass())).createInjectionTarget(null);
        injectionTarget.inject(myImplementationInstance, ctx);

注意 - 通過執行此操作,您將負責在不再需要對象后清理對象。 CreationContext存儲在某處並在其上調用release()方法以便正確處理它(使用所有可能的pre destroy調用等)。

或者,由於您已經在使用CDI,為什么第三方只是@Inject您提供的bean?

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM