6

私はここに来たばかりで、CDI の世界にも慣れていません。仕事で最初に受けた仕事は、CDI のアップロードを制御する方法を見つけることでした。

と の両方を使用してEJB 3.1CDI 1.0ます。これらは異なるコンテナーによって制御されるため、@Startup@Singletonアノテーションを使用して、EJB マネージド Bean を起動するタイミングと順序を制御できます。

しかし、@InjectCDI コンテナーがまだ開始されていないため、クラスで宣言した CDI Bean が null になります。

私は解決策を探すために数日間試みてきましたが、ここで見つけたものは機能しませんでした (まだ null として来ました)。

Java EE 6 を使用し、WebSphere Application Server 8 でアプリケーションを実行しています。

EJB に関係なく、内部で CDI のアップロードを制御する方法を見つけるのを手伝ってくれませんか?

サンプルコードは次のとおりです。

import javax.annotation.PostConstruct;
import javax.ejb.Singleton;
import javax.ejb.Startup;

@Singleton
@Startup
public class BaseStartupLoader{


/**
 * Default constructor. 
 */
@Inject @MyStartup
BaseStartUp myStartup;

private static Logger m_logger = LoggerFactory.getLogger(BaseStartupLoader.class);
public BaseStartupLoader() {

}

@PostConstruct
public void init(){

    String applicationName = null;

    try {

            applicationName = myStartup.getClass().getName();
            myStartup.load();

    } catch (IllegalAccessException e) {
        m_logger.error("Faild to load data into preload system. "+e);               
    } catch (InstantiationException e) {
        m_logger.error("Faild to load data into preload system. "+e);               
    } catch (ClassNotFoundException e) {
        m_logger.error("Faild to load data into preload system - Class "+ applicationName + "Not found. "+e);               
    }
  }
}

BaseStartup インターフェイスは次のとおりです。

public interface BaseStartUp {
public void load() throws IllegalAccessException, InstantiationException, ClassNotFoundException;
}  

修飾子と実装:

@Retention(RetentionPolicy.RUNTIME)
@Target ({ElementType.PARAMETER, ElementType.FIELD, ElementType.TYPE, ElementType.METHOD})
@Qualifier 
@Dependent
public @interface MyStartup {   
}


@MyStartup
public class MyStartUpLoader implements BaseStartUp {

    @Inject
    SomeConfigLoader config;

    @Override
    public void load() throws IllegalAccessException, InstantiationException, ClassNotFoundException {
    conifg.init();      
}   
}
4

3 に答える 3

5

多くの調査の後、私は IBM の担当者の助けを見つけました。私たちは WebSphere Application Server を使用しているので、次の名前の JVM プロパティを追加するだけです。

"com.ibm.ws.cdi.immediate.ejb.start" = true

彼は、私が作成した @Startup Bean の EJB @PostConstruct メソッドに到達すると、CDI コンテナーが既に稼働しており、既に注入されていることを確認します。

できます!!

IBM サイトの問題と解決策へのリンクは次のとおりです。

http://www-01.ibm.com/support/docview.wss?uid=swg1PM62774

于 2013-01-14T15:07:38.797 に答える
3

おそらく、CDI が必要なアプリケーションのすべての場所で実際に有効になっていることを再確認してください。BaseStartupLoader実験として、次のコードを に追加してみてください。

@Singleton
@Startup
public class BaseStartupLoader {

    @Inject @MyStartup
    BaseStartUp myStartup;

    @Inject
    private InjectionTest test;


    public static class InjectionTest {}
}

test変数が null になった@PostConstruct場合、CDI がBaseStartupLoader宣言されている jar で有効になっていない可能性があります。

たとえば、BaseStartupLoaderが と呼ばれる jar で宣言され、 と呼ばれる jarorange.jarMyStartUpLoader宣言されているyellow.jar場合、これらの両方のファイルが存在する必要があります。

  • orange.jar!/META-INF/beans.xml
  • yellow.jar!/META-INF/beans.xml

を介して両方の jar で CDI が適切に有効になっている場合META-INF/beans.xml、これはコンテナーのバグです。呼び出される前に、すべての@Injectポイントを完了する必要があります (CDI 対応の jar の場合) 。@PostConstructこれは、@Startupが使用されていて、Bean の 1 つがたまたま EJB であるかどうかに関係なく当てはまります。

于 2012-12-25T00:11:11.663 に答える
0

DeltaSpikeを見てください。あなたが今探していることをするはずのCDIコントロールモジュールがあります。JavaEE7でもこれを修正する必要があると思います。

于 2012-12-25T19:41:27.017 に答える