CDI1.1から追加されたbean-discovery-mode
このエントリーは「Java EE Advent Calendar 2013 - Adventar」の5日目のエントリーです。
4日目は@kazuhira_rさんの「Standard Caching - CLOVER」でした。
6日目は@normalianさんです。よろしくお願いします。
【概要】
CDI1.1から追加されたbean-discovery-modeについて書きます。
CDI1.0ではbeans.xmlに何も設定を行わない場合、
全てのクラスがインジェクション対象になります。
CDI1.1からはインジェクションの対象を
検索するモードを指定できるようになりました。
【3つのモード】
bean-discovery-modeで指定できるのは
annotated、all、noneの3つです。
[annotated]
CDI1.1のデフォルト値です。
annotatedを指定した場合は
スコープアノテーションを指定してクラスがインジェクション対象となります。
[all]
全てのクラスがインジェクション対象となります。
CDI1.0と同じような動きをします。
【サンプルソースについて】
bean-discovery-modeのannotatedとallの動きを試してみます。
JAX-RSのリソースクラスから
オブジェクトをインジェクションさせるサンプルです。
SampleInjectionClassクラスがインジェクション対象、
SampleStubクラスはインジェクション対象外にします。
2つのクラスはSampleInterfaceインターフェイスを実装しています。
【前提となるクラス】
[SampleApplication]
JAX-RSのアプリケーションパスを指定しています。
@ApplicationPath("/sample") public class SampleApplication extends Application { }
[SampleResource]
SampleResourceクラスから
SampleInterfaceインターフェイスのオブジェクトを
インジェクションしています。
@Path("/annotated") @RequestScoped public class SampleResource implements Serializable { @Inject private SampleInterface injectionObject = null; @POST public Response executeSample() { injectionObject.execute(); return Response.ok("Method is complete.").build(); } }
【allモード】
まずはallモードです。
[beans.xml]
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="all"> <scan> <exclude name="jp.glory.sample.service.stub.**" /> </scan> </beans>
bean-discovery-modeにallを指定します。
name属性にはワイルドカードが使用できます。
サンプルではSampleStubクラスがあるパッケージを
インジェクション対象外として指定します。
[SampleInjectionClass / SampleStub]
インジェクション対象のクラスは
インターフェイスを実装するだけです。
public class SampleStub implements SampleInterface { // 何かしらの処理 } public class SampleInjectionClass implements SampleInterface, Serializable { // 何かしらの処理 }
allモードなので全てのクラスがインジェクション対象となりますが、
【annotatedモード】
続いてannotatedモードです。
[beans.xml]
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd" bean-discovery-mode="annotated"> </beans>
annotatedモードではbean-discovery-mode属性にannotatedを指定するだけです。
[SampleStub]
インジェクション対象外のクラスです。
public class SampleStub implements SampleInterface { // 何かしらの処理 }
インジェクション対象外とするクラスには
特に何もアノテーションを指定しません。
【まとめ】
bean-discovery-modeの
annnotated、allをまとめると↓のようになります。
- annotated
- インジェクション対象を指定する方式
- all
- インジェクション対象外を指定する方式
annotatedだと一つ一つ指定するのでやや面倒くさそうだけど、
意図しないインジェクションが防げそう。
allだと基本的に少ない指定でできるけど、
意図しないインジェクションが紛れ込みそう。
と言うのが個人的な感想です。
私は明示的にやりたいので、annotatedをお勧めしたいです。