6

管理対象 Bean の CDI の GlassFish 3.1 実装では、コンストラクター注入はサポートされていますか? @Singletonコンストラクター注入を使用して別のマネージド Bean (同じ EJB モジュールに含まれる) を注入したい EJB があります。フィールドインジェクションは機能します。しかし、コンストラクター注入を使用すると、NullPointerExceptionfrom AbstractSingletonContainer.

これは機能します:

@Singleton
public class FooBean implements Foo {

  @Inject private BarBean bar;

}

これは動作しません:

@Singleton
public class FooBean implements Foo {

    private final BarBean bar;

    @Inject
    public FooBean(BarBean bar) {
        this.bar = bar;
    }

}
4

2 に答える 2

10

CDIは、直接フィールドインジェクション、初期化子メソッドパラメーターインジェクション、およびコンストラクターパラメーターインジェクションをサポートします。CDI 1.0仕様から:

3.7。Beanコンストラクター

コンテナがBeanクラスをインスタンス化するとき、Beanコンストラクタを呼び出します。Beanコンストラクターは、Beanクラスのコンストラクターです。

アプリケーションは、Beanコンストラクターを直接呼び出すことができます。ただし、アプリケーションがBeanを直接インスタンス化する場合、コンテナーによってコンストラクターにパラメーターが渡されることはありません。返されたオブジェクトはどのコンテキストにもバインドされていません。コンテナによって依存関係が注入されることはありません。また、新しいインスタンスのライフサイクルはコンテナによって管理されません。

3.7.1。Beanコンストラクターの宣言

Beanコンストラクターは、コンストラクターに注釈を付けることで識別できます @Inject

@SessionScoped
public class ShoppingCart implements Serializable {
    private User customer;

    @Inject
    public ShoppingCart(User customer) {
        this.customer = customer;
    }

    public ShoppingCart(ShoppingCart original) {
        this.customer = original.customer;
    }

    ShoppingCart() {}

    ...
}

@ConversationScoped
public class Order {
    private Product product;
    private User customer;

    @Inject
    public Order(@Selected Product product, User customer) {
        this.product = product;
        this.customer = customer;
    }

    public Order(Order original) {
        this.product = original.product;
        this.customer = original.customer;
    }

    Order() {}

    ...
}

Beanクラスがを使用してコンストラクターを明示的に宣言していない場合、@Injectパラメーターを受け入れないコンストラクターはBeanコンストラクターです。

Beanクラスに複数のコンストラクターに注釈が付けられている@Inject場合、コンテナーは問題を自動的に検出し、それを定義エラーとして扱います。

@DisposesBeanコンストラクターに、またはの注釈が付けられたパラメーターがある場合@Observes、コンテナーは問題を自動的に検出し、それを定義エラーとして扱います。

Beanコンストラクターには、任意の数のパラメーターを含めることができます。Beanコンストラクターのすべてのパラメーターはインジェクションポイントです。

しかし、あなたの問題はWELD-141に関連しているのではないかと思います。

参考文献

  • CDI1.0仕様
    • セクション3.7。「Beanコンストラクター」
  • 溶接ドキュメント
于 2010-08-23T06:56:04.363 に答える
4

コンストラクター注入は GlassFish 3.x でサポートされていますが、EJB の仕様を満たすには、とにかくデフォルトのコンストラクターを提供する必要があります。

これはうまくいきます:

@Singleton
public class FooBean implements Foo {

    private final BarBean bar;

    public FooBean() {
      this.bar = null;
    }

    @Inject
    public FooBean(BarBean bar) {
        this.bar = bar;
    } 
}

ただし、Glassfish (この部分はコンテナーに依存します)は、注入されたコンストラクターの前にデフォルトのコンストラクターを呼び出します。

于 2013-02-17T14:15:43.463 に答える