8 Java EEアノテーションと依存関係インジェクションの使用
この章の内容は次のとおりです。
- アノテーションの処理
アノテーションを使用すると、コンテナ内でのアプリケーション・コンポーネントの動作、依存関係インジェクションのリクエスト方法などをJavaクラス自体の中で指定でき、アプリケーションの開発プロセスを簡略化できます。アノテーションは、エンタープライズ・アプリケーションの以前のバージョン(Java EE 1.4以前)で必要とされたデプロイメント記述子にかわるものです。 - リソースの依存関係インジェクション
依存関係インジェクション(DI)を使用することで、アプリケーション・コンポーネントで外部リソースおよび構成パラメータに対する依存関係をアノテーションを介して宣言できます。コンテナはこれらのアノテーションを読み込み、リソースまたは環境エントリをアプリケーション・コンポーネントに注入します。 - 標準のJDKアノテーション
標準のJDKアノテーションに関連するいくつかのリファレンス情報について検討します。 - 標準のセキュリティ関連JDKアノテーション
標準のセキュリティ関連のJDKアノテーションに関連するいくつかのリファレンス情報について検討します。
アノテーションの処理
アノテーションを使用すると、コンテナ内でのアプリケーション・コンポーネントの動作、依存関係インジェクションのリクエスト方法などをJavaクラス自体の中で指定でき、アプリケーションの開発プロセスを簡略化できます。アノテーションは、エンタープライズ・アプリケーションの以前のバージョン(Java EE 1.4以前)で必要とされたデプロイメント記述子にかわるものです。
Java EEアノテーションの使用により、標準のapplication.xml
およびweb.xml
デプロイメント記述子は省略可能になりました。このJava EEプログラミング・モデルでは、EJB、サーブレット、Webアプリケーション、JSPなどのWebコンテナ用のJDKアノテーション機能を使用します(http://docs.oracle.com/javaee/6/api/
を参照)。
アノテーションの解析
アプリケーション・コンポーネントでは、必要なものの定義にアノテーションを使用できます。アノテーションを使用すると、デプロイメント記述子を扱う必要がなくなります。アノテーションにより、アプリケーション・コンポーネントの開発は簡略化されます。引続きデプロイメント記述子により、アノテーションで定義した値をオーバーライドすることもできます。アノテーション使用の一例としては、依存関係インジェクション(DI)を必要とするフィールドまたはメソッドの定義が挙げられます。アノテーションは、EJBやサーブレットのような、POJO (プレーンな従来型Javaオブジェクト)コンポーネント・クラスに対して定義されます。
フィールドまたはメソッド上のアノテーションでは、「リソースの依存関係インジェクション」に記載のとおり、フィールドやメソッドが注入を必要とすることを宣言できます。また、クラス自体にアノテーションを適用することもできます。クラス・レベルのアノテーションは、アプリケーション・コンポーネントの環境内でエントリを宣言しますが、リソースの注入にはつながりません。むしろ、アプリケーション・コンポーネントでは、JNDIまたはコンポーネント・コンテキスト・ルックアップ・メソッドを使用してエントリをルックアップすることが前提となっています。アノテーションをクラスに適用する際には、JNDI名および環境エントリ・タイプを明示的に指定する必要があります。
親トピック: アノテーションの処理
アノテーション構成のデプロイメント表示
Java EE開発API [JSR88]を使用すると、開発者はデプロイメント記述子を調べることができます。たとえば、デプロイメント記述子のないEJBモジュールの場合を考えます。このモジュールには、アノテーションを使用するEJBとして宣言されたクラスがあることが前提です。Session Helperのユーザーは、引き続きモジュールをデプロイメント記述子がある場合と同様に扱えます。したがって、開発者は構成情報を修正でき、その情報はデプロイメント・プランに書き出されます。デプロイメント中はこれらのプランが尊重され、アノテーションからの情報をオーバーライドします。
親トピック: アノテーションの処理
アノテーション付きクラスのコンパイル
WebLogic Serverユーティリティappc
(およびそれに対応するAnt wlappc
とAppmerge
)では、メタデータ・アノテーションをサポートしています。appmerge
およびappc
ユーティリティは、アプリケーションまたはモジュールを入力として取り、それらを処理して、それぞれ出力アプリケーションまたはモジュールとして生成します。-writeInferredDescriptors
フラグと一緒に使用すると、出力アプリケーションまたはモジュールには、アノテーション情報と共にデプロイメント記述子が含まれます。また記述子では、出力アプリケーションまたはモジュールが直接デプロイされるのであれば、実行の必要なアノテーション処理はないため、metadata-complete
属性がtrue
に設定されます。ただし、以前に処理されたアプリケーションまたはモジュールでこれらのツールが呼び出された場合、metadata-complete
属性がtrue
に設定されていると、appmerge
およびappc
がアノテーションの処理について制限を受けます。
そのような場合、.orig
接尾辞によって、本来の記述子を保持する必要があります。出力アプリケーションに対してアノテーションの処理を再適用する場合、開発者は記述子を復元して、もう一度-writeInferredDescriptors
フラグを使用する必要があります。appmerge
またはappc
が、標準のデプロイメント記述子の存在しないエンタープライズ・アプリケーションで、-writeInferredDescriptors
とともに使用されると、記述子が生成され、Java EE仕様の推論ルールに基づき、書き出されます。
appc
の使用の詳細は、「weblogic.appcリファレンス」を参照してください。appmerge
の使用の詳細は、「weblogic.appmergeを使用したライブラリの結合」を参照してください。
親トピック: アノテーションの処理
アノテーションの動的な更新
デプロイされたモジュールは、update
デプロイメント操作を使用して更新できます。そのような更新において、デプロイメント記述子または更新されたクラスに変更があった場合、コンテナでは新しいデプロイメント記述子を処理する一方で、アノテーション情報を再度検討する必要があります。
コンテナでは、記述子フレームワークの2フェーズの更新メカニズムを使用して、現在の記述子と提案されている記述子の相違点を確認します。このメカニズムはまた、動的でないプロパティに変更があった場合も、コンテナにそれを通知します。その後、コンテナはそのような動的でない変更を、独自の特定的な方法によって処理します。コンテナでは、正しい参照との相違点を確実に発見するため、提案された記述子に対しアノテーション処理を実行する必要があります。
同様に、モジュールのクラスの一部は、更新処理中に更新可能です。これらのクラスがアノテーションを通じて構成情報に影響を与えることがあり得るとわかった場合、コンテナは変更が加えられることを回避します。
親トピック: アノテーションの処理
リソースの依存関係インジェクション
依存関係インジェクション(DI)を使用することで、アプリケーション・コンポーネントで外部リソースおよび構成パラメータに対する依存関係をアノテーションを介して宣言できます。コンテナはこれらのアノテーションを読み込み、リソースまたは環境エントリをアプリケーション・コンポーネントに注入します。
依存関係インジェクションは、リソースのルックアップをjavax
インタフェースまたはJNDI APIを使用して行うことにかわる、非常に簡単なプログラミング方法です。
アプリケーション・コンポーネントのフィールドまたはメソッドには、@Resource
アノテーションを付けることができます。コンテナは、必要に応じて環境エントリを解放し、インジェクション・フィールドまたはメソッドに使用されるプリミティブ型に一致させます。例8-1は、アプリケーション・コンポーネントで@Resource
アノテーションを使用して環境エントリを宣言する方法を示しています。
例8-1 環境エントリの依存関係インジェクション
// fields // The maximum number of tax exemptions, configured by the Deployer. @Resource int maxExemptions; // The minimum number of tax exemptions, configured by the Deployer. @Resource int minExemptions; ….. }
前述のコードでは、@resource
アノテーションは名前を指定していません。したがって、コンテナは<
class-name
>/maxExemptions
というenv-entry
名を探し、そのエントリの値をmaxExemptions
変数に注入します。フィールドまたはメソッドには、任意のアクセス修飾子(public、privateなど)を指定できます。アプリケーション・クライアントのメイン・クラス以外のすべてのクラスについて、フィールドまたはメソッドは、静的なものとする必要があります。アプリケーション・クライアントは、Java EEアプリケーションと同じライフサイクルを使用するため、アプリケーション・クライアントのメイン・クラスのインスタンスが、アプリケーション・クライアントのコンテナによって作成されることはありません。その代わり、静的なmainメソッドが呼び出されます。アプリケーション・クライアントのメイン・クラスに対する注入をサポートするため、注入用にアノテーションを付けられるフィールドまたはメソッドは静的であることが必要です。
アプリケーション・ライフ・サイクル・アノテーション・メソッド
アプリケーション・コンポーネントでは、すべてのリソースが注入された後で、独自に初期化を実行する必要がある場合があります。このケースをサポートするため、クラスのメソッドの1つに、@PostConstruct
アノテーションを付けることができます。このメソッドは、すべての注入が行われた後、クラスのサービスが開始される前に呼び出されます。このメソッドは、クラスが注入されるリソースをリクエストしていなくても呼び出されます。同様に、コンテナによってライフサイクルを管理されているクラスでは、クラスのサービスが終了し、これ以上はコンテナによって使用されなくなったときに呼び出される、1つのメソッドに@PreDestroy
アノテーションを適用できます。クラス階層構造内の各クラスに、@PostConstruct
メソッドと@PreDestroy
メソッドを指定できます。
メソッドの呼出し順は、クラス階層構造における順序に一致しており、スーパークラスに対するメソッドが、サブクラスに対するメソッドよりも前に呼び出されます。Java EE側からは、これらのJava EEクライアントのライフサイクル・メソッドの呼び出しに関与しているのは、アプリケーション・クライアント・コンテナのみです。Java EEクライアントのライフサイクル・メソッドは静的であることが必要です。Java EEクライアントは、@PostConstruct
コールバックをサポートするのみです。
親トピック: リソースの依存関係インジェクション
標準のJDKアノテーション
標準のJDKアノテーションに関連するいくつかのリファレンス情報について検討します。
WebLogic Server Enterprise JavaBeansに対するEJB固有のアノテーションの詳細は、『Oracle WebLogic Server Enterprise JavaBeansの開発』を参照してください。
WebLogic Serverアプリケーションに対するWebコンポーネント固有のアノテーションの詳細は、『Oracle WebLogic Server Webアプリケーション、サーブレット、JSPの開発』のWebコンポーネント用のWebLogicアノテーションに関する項を参照してください。
javax.annotation.PostConstruct
ターゲット: メソッド
初期化を実行するために、依存関係インジェクションが完了した後、1番目のビジネス・メソッドを呼び出す前にアプリケーション・コンポーネントから呼び出す必要のあるライフサイクル・コールバック・メソッドを指定します。このメソッドは、すべての注入が行われた後、クラスのサービスが開始される前に呼び出されます。このメソッドは、クラスが注入されるリソースをリクエストしていなくても呼び出されます。
依存関係インジェクションを含むすべてのコンポーネントには、@PostConstruct
メソッドを指定する必要があります。
このアノテーションは、コンポーネント内の1つのメソッドにのみ付けることができます。
@PostConstruct
アノテーションを付けるメソッドは、以下の要件を満たす必要があります。
-
メソッドにパラメータを指定してはいけません - ただし、EJBインターセプタの場合にかぎり、EJB仕様で定義されているとおりjavax.interceptor.InvocationContextオブジェクトを取ります。
-
メソッドの戻り値の型が
void
でなければなりません。 -
検査済みの例外をスローしてはいけません。
-
public
、protected
、package private
、またはprivate
にすることは可能です。 -
アプリケーション・クライアントの場合を除いて、メソッドは
static
であってはいけません。 -
メソッドは
final
でもnon-final
でもかまいませんが、EJBの場合はnon-final
とする必要があります。 -
メソッドが未検査の例外をスローした場合、クラスはサービスを開始してはいけません。EJBの場合、PostConstructアノテーションの付いたメソッドは、beanインスタンスが破棄される前に例外およびクリーン・アップを処理できます。
このアノテーションには、属性はありません。
親トピック: 標準のJDKアノテーション
javax.annotation.PreDestroy
ターゲット: メソッド
アプリケーション・コンポーネントがコンテナによって破棄されようとしていることを通知するライフサイクル・コールバック・メソッドを指定します。通常、このアノテーションは、クラスが保持しているリソースを解放するメソッドに適用します。
このアノテーションは、Beanクラス内の1つのメソッドにのみ付けることができます。
@PreDestroy
アノテーションを付けるメソッドは、以下の要件を満たす必要があります。
-
メソッドにパラメータを指定してはいけません - ただし、EJBインターセプタの場合にかぎり、EJB仕様で定義されているとおりjavax.interceptor.InvocationContextオブジェクトを取ります。
-
メソッドの戻り値の型が
void
でなければなりません。 -
検査済みの例外をスローしてはいけません。
-
public
、protected
、package private
、またはprivate
にすることは可能です。 -
アプリケーション・クライアントの場合を除いて、メソッドは
static
であってはいけません。 -
メソッドは
final
でもnon-final
でもかまいませんが、EJBの場合はnon-final
とする必要があります。 -
メソッドが未検査の例外をスローした場合、クラスはサービスを開始してはいけません。EJBの場合、
PreDestroy
アノテーションの付いたメソッドは、beanインスタンスが破棄される前に例外およびクリーン・アップを処理できます。
このアノテーションには、属性はありません。
親トピック: 標準のJDKアノテーション
javax.annotation.Resource
ターゲット: クラス、メソッド、フィールド
外部リソース(JDBCデータ・ソース、JMS宛先、接続ファクトリなど)への依存関係を指定します。
このアノテーションをフィールドまたはメソッドに指定すると、Beanの初期化時に、リクエストされたリソースのインスタンスがBeanに注入されます。このアノテーションをクラスに適用すると、コンポーネントが実行時にルックアップするリソースが宣言されます。
属性
表8-1 javax.annotation.Resourceアノテーションの属性
名前 | 説明 | データ型 | 必須? |
---|---|---|---|
|
リソースのJNDI名を指定します。
|
|
いいえ |
|
リソースのJavaデータ型を指定します。
|
|
いいえ |
|
このリソースに使用する認証タイプを指定します。 この属性の有効な値は以下のとおりです。
デフォルト値は |
|
いいえ |
|
リソースを、このコンポーネントと他のコンポーネントとの間で共有できるかどうかを指定します。 この属性の有効な値は、 |
|
いいえ |
|
コンポーネント参照をマップするWebLogic Server固有の名前を指定します。 ただし、WebLogicデプロイメント記述子ファイル内でJNDI名を指定しない場合、ルックアップされるJNDI名として
つまり、 |
|
いいえ |
|
リソースの説明を指定します。 |
|
いいえ |
親トピック: 標準のJDKアノテーション
javax.annotation.Resources
ターゲット: クラス
@Resource
アノテーションの配列を指定します。アノテーションの繰返しは許可されていないため、Resourcesアノテーションは、複数のリソース宣言のコンテナとして機能します。
属性
表8-2 javax.annotation.Resourcesアノテーションの属性
名前 | 説明 | データ型 | 必須? |
---|---|---|---|
|
|
|
はい |
親トピック: 標準のJDKアノテーション
標準のセキュリティ関連JDKアノテーション
標準のセキュリティ関連のJDKアノテーションに関連するいくつかのリファレンス情報について検討します。
javax.annotation.security.DeclareRoles
ターゲット: クラス
Java EEコンテナで使用されるセキュリティ・ロールを定義します。
通常、このアノテーションは、アノテーションを付けたクラスのメソッド内から(たとえばisUserInRole
メソッドを使用して)テストできるロールを定義するために使用します。また、クラスまたはクラスのメソッドで@RolesAllowed
アノテーションを使用している場合はロールが暗黙的に宣言されますが、このアノテーションを使用することでそれらのロールを明示的に宣言できます。
セキュリティ・ロールは、WebLogic ServerでWebLogic Server管理コンソールを使用して作成できます。セキュリティの詳細は、セキュリティ・ロールに関する項を参照してください。
属性
表8-3 javax.annotation.security.DeclareRolesアノテーションの属性
名前 | 説明 | データ型 | 必須? |
---|---|---|---|
|
Java EEコンテナ内で使用するセキュリティ・ロールの配列を指定します。 |
|
はい |
親トピック: 標準のセキュリティ関連JDKアノテーション
javax.annotation.security.DenyAll
ターゲット: メソッド
このアノテーションを付けたメソッドへのアクセスを、どのセキュリティ・ロールにも許可しないことを指定します。つまり、このメソッドは、Java EEコンテナでの実行から除外されます。
このアノテーションには、属性はありません。
親トピック: 標準のセキュリティ関連JDKアノテーション
javax.annotation.security.PermitAll
ターゲット: メソッド
このアノテーションを付けたメソッドへのアクセスを、WebLogic Serverに定義されているすべてのセキュリティ・ロールに許可することを指定します。
このアノテーションには、属性はありません。
親トピック: 標準のセキュリティ関連JDKアノテーション
javax.annotation.security.RolesAllowed
ターゲット: クラス、メソッド
Java EEコンテナ内のメソッドにアクセスできるセキュリティ・ロールのリストを指定します。
クラス・レベルで指定した場合は、アプリケーション・コンポーネント内のすべてのメソッドに適用されます。メソッド・レベルで指定した場合は、そのメソッドにのみ適用されます。このアノテーションをクラス・レベルとメソッド・レベルの両方で指定した場合は、クラス・レベルの値がメソッド・レベルの値によってオーバーライドされます。
セキュリティ・ロールは、WebLogic ServerでWebLogic Server管理コンソールを使用して作成できます。セキュリティの詳細は、セキュリティ・ロールに関する項を参照してください。
属性
表8-4 javax.annotation.security.RolesAllowedアノテーションの属性
名前 | 説明 | データ型 | 必須? |
---|---|---|---|
|
Java EEコンテナのメソッドにアクセスできるセキュリティ・ロールのリストを指定します。 |
|
はい |
親トピック: 標準のセキュリティ関連JDKアノテーション
javax.annotation.security.RunAs
ターゲット: クラス
Java EEコンテナを実際に実行するセキュリティ・ロールを指定します。
指定するセキュリティ・ロールは、WebLogic Serverのセキュリティ・レルム内に存在し、ユーザーまたはグループにマッピングされている必要があります。セキュリティの詳細は、セキュリティ・ロールに関する項を参照してください。
属性
表8-5 javax.annotation.security.RunAsアノテーションの属性
名前 | 説明 | データ型 | 必須? |
---|---|---|---|
|
Java EEコンテナが実行されるセキュリティ・ロールを指定します。 |
|
はい |
親トピック: 標準のセキュリティ関連JDKアノテーション