SlideShare une entreprise Scribd logo
1  sur  90
Télécharger pour lire hors ligne
CDI2.0アップデート	
& クックブック	
2016/05/24 上妻 宜人 (あげつま のりと)	
Java Day Tokyo 2016/Java EE Session 4-C
上妻 宜人 あげつま のりと	
•  SIer技術部門でJavaトラブルシューティングの日々	
•  Java EEについて調べて伝えることが好き	
•  コミュニティ講演	
•  GlassFish.JP, JJUG CCC, Java Day Tokyo 2015 など
本日のコンテンツ	
•  駆け足で振り返るCDI	
•  CDI2.0	
•  CDI + α 	
•  最後に
CDI	Context	and	Dependency	Injec0on	
2009/12	CDI1.0	-	Java	EE	6	
2013/5			CDI1.1	-	Java	EE	7	
2014/4			CDI1.2			(maintenance	release)	
2017/1			CDI2.0	-	Java	EE	8
CDIの目的	
1.	DI/AOPを中心とした疎結合コードの実現	
					@Inject,	@InterceptorBinding,	@Decorator,	Event	
	
2.	コンテキストを持つオブジェクトのライフサイクル管理	
					@RequestScoped,	@SessionScoped,	@Applica0onScoped	...	
3.	EJB	SessionBean	と	JSF	@ManagedBean	の統合
CDI	実装製品	
•  Weld	(参照実装)	-	jboss.org	
•  GlassFish,	WildFly/JBossEAP,	WebLogic	
•  OpenWebBeans	-	Apache	SoZware	Founda0on	
•  WebSphere,	Apache	TomEE
Context	and	Dependency	Injec0on:	
CDI管理Beanの定義	
// ライフサイクル: デプロイ〜アンデプロイまで%
public class Controller {%
%
%
}%
%
%
// ライフサイクル: ユーザセッションごとに生成、ログアウトで破棄%
public class ShoppingCart implements Cart {...}%
%
Context	and	Dependency	Injec0on:	
ランタイム例外を引き起こすコンテキスト操作	
public class Controller { %
...%
HttpSession session = request.getSession();%
session.setAttribute(“shoppingCart”,	new	ShoppingCart());%
%
....%
%
Cart cart = (Cart)session.getAttribute(“shopingCart”);%
Context	and	Dependency	Injec0on:	
CDI管理Beanの定義	
@ApplicationScoped%
public class Controller {%
%
%
}%
%
%
@SessionScoped%
public class ShoppingCart implements Cart {...}%
%
@ApplicationScoped%
public class Controller {%
%
%
}%
%
%
@SessionScoped%
public class ShoppingCart implements Cart {...}%
%
Scope	
•  @RequestScoped	
•  @SessionScoped	
•  @Applica0onScoped	
•  @Conversa0onScoped	
•  @Dependent	
Context	and	Dependency	Injec0on:	
CDI管理Beanのスコープ
Context	and	Dependency	Injec0on:	
@Injectでタイプセーフに取得	
@ApplicationScoped%
public class Controller {%
@Inject%
Cart cart;%
}%
%
%
@SessionScoped%
public class ShoppingCart implements Cart {...}%
%
CDIコンテナがインスタンスをセット
Context	and	Dependency	Injec0on:	
@InterceptorBinding	-		タイプセーフなインターセプタ適用	
Log	 target	
// target%
@ApplicationScope%
public class OrderService {%
public void submit(Order order) {..}%
}%
// Log%
@Interceptor%
public class LogInterceptor {...}%
Context	and	Dependency	Injec0on:	
@InterceptorBinding	-		タイプセーフなインターセプタ適用	
Log	 target	
// target%
@ApplicationScope%
public class OrderService {%
public void submit(Order order) {..}%
}%
// Log%
@Interceptor%
public class LogInterceptor {...}%
@Inherited%
@InterceptorBinding%
@Target({TYPE, METHOD})%
@Retention(RUNTIME)%
public @interface Log {}
Context	and	Dependency	Injec0on:	
@InterceptorBinding	-		タイプセーフなインターセプタ適用	
Log	 target	
// target%
@ApplicationScope @Log%
public class OrderService {%
public void submit(Order order) {..}%
}%
// Log%
@Interceptor @Log%
public class LogInterceptor {...}%
@Inherited%
@InterceptorBinding%
@Target({TYPE, METHOD})%
@Retention(RUNTIME)%
public @interface Log {}	
Binding
CDI1.1の変更点 (Java	EE	7)		
beans.xmlのオプション化	
•  beans.xmlなしでCDI有効化	
•  スコープを持つクラスはすべてCDI管理Bean	
@RequestScoped, @SessionScoped, @ApplicationScoped ...	
•  @Dependentスコープは明示的に付与が必要	
// Java EE 7デフォルトでは@Dependent省略不可%
@Dependent%
public class DependentBean {...}%
CDI1.1の変更点 (Java	EE	7)	
beans.xmlのオプション化	
•  @Priority	
•  主にインターセプタ有効化 & 優先順位付けに使用	
•  Interceptorの有効化にbeans.xmlが不要に	
@Interceptor%
@Priority(Interceptor.Priority.APPLICATION)%
public class LoggingInterceptor { %
@AroundInvoke%
public Object log(InvocationContext ic) %
throws Exception {...}%
}
CDI1.1の変更点 (Java	EE	7)	
@Priorityによるインターセプト順序の定義	
@Interceptor @Timeout%
@Priority(Interceptor.Priority.APPLICATION + 10)%
public class TimeoutInterceptor {...}%
Log	
@Interceptor @Logging%
@Priority(Interceptor.Priority.APPLICATION)%
public class LogInterceptor {...}%
【値が小さいほど早く起動】%
Priority.PLATFORM_BEFORE: 0%
@Transactional = 200%
Priority.LIBRARY_BEFORE: 1000%
Priority.APPLICATION: 2000%
アプリケーション向け有効範囲:〜2999%
Time	
out	 target	
Priority:		2000													2010
CDI1.1の変更点 (Java	EE	7)	
スコープ開始・終了イベント	
@ApplicationScoped%
public class MasterDataCache {%
public void observer(%
@Observes @Initialized(ApplicationScoped.class)%
ServletContext context) {%
// initilize code%
}%
}%
•  スコープの開始・終了タイミングでイベント発火	
•  Applica0onScopedの場合@Startup代わりに使える
CDI1.2の変更点 (Java	EE	7)	
JSR-330との互換性確保	
•  @javax.inject.Singletonをスキャン対象外へ	
•  デフォルトでは@SingletonはCDI管理Beanと見なされない	
•  代わりに @ApplicationScoped を使う	
•  背景はGuavaを含むAPがCDI1.1からデプロイエラーになったこと	
	
Guava	14.0.1	cannot	be	deployed	in	a	JEE7	Container	#1433	
https://github.com/google/guava/issues/1433
本日のコンテンツ	
•  駆け足で振り返るCDI	
•  CDI2.0 	
•  CDI + α	
•  最後に
CDI2.0	(Java	EE	8	/	2017)	
•  	CDI非同期イベント	
•  	仕様をサブセットに分割	
•  	Java	SE	Support	
•  	Java	SE	8	Alignment
@ApplicationScoped%
public class AlertService {%
@Inject AlertRepository repo;%
%
@Transactinal%
public void handleAlert(Alert alert) {%
// 何らかのビジネスロジックを終えた後に ...%
repo.persist(alert);%
}%
}	
通常のメソッド呼び出し	
最初はシンプルな機能	
Alert	
Service	
Alert	
Repository
@ApplicationScoped%
public class AlertService {%
@Inject AlertRepository repo;%
@Inject EmailSender email;%
%
@Transactinal%
public void handleAlert(Alert alert) {%
// 何らかのビジネスロジックを終えた後に ...%
repo.persist(alert);%
email.send(“test@test.com”, alert);%
}%
}	
通常のメソッド呼び出し	
アラートが来たらメールも	...	
Alert	
Service	
Alert	
Repository	
Email	
Sender
@ApplicationScoped%
public class AlertService {%
@Inject AlertRepository repo;%
@Inject EmailSender email;%
@Inject AlertCache cache;%
%
@Transactinal%
public void handleAlert(Alert alert) {%
// 何らかのビジネスロジックを終えた後に ...%
repo.persist(alert);%
email.send(“test@test.com”, alert);%
cache.putIfAbsent(alert);%
}%
}	
通常のメソッド呼び出し	
アラートが来たらキャッシュ更新も	...	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache
通常のメソッド呼び出し	
手続き型のデメリット	
•  機能追加毎にクラス間依存性が増加	
•  やがては蜘蛛の巣になる	
•  CDI管理Beanが持つ状態のロールバックが難しい	
•  宣言的トランザクションがコミット失敗した場合、	
トランザクション中に変更したBeanのステートをどう戻すか	
•  catch節で頑張れるが、長くなることも
CDIイベントの振り返り	
イベント発火側のコード	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache	
CDI	Event	
@ApplicationScoped%
publilc class AlertService {%
@Inject AlertRepository repo;%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
repo.persist(alert);%
event.fire(alert);%
...%
%
CDIイベントの振り返り	
オブザーバの実装	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache	
CDI	Event	
@ApplicationScoped%
publilc class AlertService {%
@Inject AlertRepository repo;%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
repo.persist(alert);%
event.fire(alert);%
...%
@ApplicationScoped%
public class AlertCache {%
...%
public void updateCache(@Observes Alert alert) {%
cache.putIfAbsent(alert.getId(), alert);%
}%
}
CDIイベントの振り返り	
イベントの発火	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache	
CDI	Event	
@ApplicationScoped%
publilc class AlertService {%
@Inject AlertRepository repo;%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
repo.persist(alert);%
event.fire(alert);%
...%
@ApplicationScoped%
public class AlertCache {%
...%
public void updateCache(@Observes Alert alert) {%
cache.putIfAbsent(alert.getId(), alert);%
}%
}	
イベントと同じ引数を持つ	
全てのオブザーバに通知
CDIイベントの振り返り	
イベントモデルの一般的な利点	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache	
CDI	Event	
Alert	
Service	
Alert	
Repository	
Email	
Sender	
Alert	
Cache	
•  プラグイン構造	
•  既存に手を入れずにObserver追加で拡張	
•  実行タイミング/場所の分離	
•  非同期実行、別マシンでの実行が理論上は可能となる
CDI	
Container	
Subject	
@Observe	
Observer	#1	
@Observe	
Observer	#2	
1.fire()	
2.call	back	#1	
3.call	back	#2
CDI	
Container	
Subject	
@Observe	
Observer	#1	
@Observe	
Observer	#2	
1.fire()	
thread	
2.call	back	#1	
3.call	back	#2	
fire()の完了	
CDI1.2までは同期呼び出しのみ
CDI2.0	#1	
CDI2.0	非同期イベント
CDI2.0	非同期CDIイベント	
イベント発火側の実装	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
event.fire(alert);%
...%
%
CDI2.0	非同期CDIイベント	
イベント発火側の実装	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
event.fireAsync(alert);%
...%
%
CDI2.0	非同期CDIイベント	
イベント発火側の実装	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
%
public void handleAlert(Alert alert) {%
event.fireAsync(alert);%
...%
%
CDI2.0	EDR1ではObserver側	
スレッドはコンテナ実装依存	
Weld	3.0.0.Alpha16の場合:		
Weld自体が持つスレッドプールを使用	
(max-size	->	CPUコア数)
CDI2.0	非同期CDIイベント	
コンテナ管理スレッドの利用 (Concurrency	U0li0es	for	Java	EE)	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
@Resource ManagedExecutor executor;%
%
public void handleAlert(Alert alert) {%
event.fireAsync(alert, executor);%
...%
%
CDI2.0	非同期CDIイベント	
全オブザーバの終了待ち受け	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
@Resource ManagedExecutor executor;%
%
public void handleAlert(Alert alert) {%
CompletionStage<Alert> asyncEvent = %
event.fireAsync(alert, executor);%
// block until complete observes%
asyncEvent.toCompletableFuture().join(); %
...%
%
CDI2.0	非同期CDIイベント	
Observer側の実装	
@ApplicationScoped%
publilc class AlertCache {%
%
ConcurrentMap<Long, Alert> cache = ...;%
%
public void updateCache(@Observes Alert alert) {%
cache.putIfAbsent(alert.getId(), alert);%
}%
} %
CDI2.0	非同期CDIイベント	
Observer側の実装	
@ApplicationScoped%
publilc class AlertCache {%
%
ConcurrentMap<Long, Alert> cache = ...;%
%
public void updateCache(@ObserveAsync Alert alert) {%
cache.putIfAbsent(alert.getId(), alert);%
}%
} %
CDI	
Container	
Subject	
@ObserveAsync	
Observer	#1	
@ObserveAsync	
Observer	#2	
fireAsync()	
call	back	
call	back	
fireAsync()は即座にreturnし、	
各Observerは別スレッドで実行	
Request	thread	
Event	thread
CDI	
Container	
Subject	
@ObserveAsync	
Observer	#1	
@ObserveAsync	
Observer	#2	
call	back	
call	back	
transac0on	#1	
transac0on	#2	
tx	#3	
トランザクション・コンテキストは	
オブザーバに引き継がれない	
Request	thread	
Event	thread	
call	back	
fireAsync()
CDI2.0	非同期CDIイベント	
Observerから例外がスローされたらどうなる?	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
@Resource ManagedExecutor executor;%
%
public void handleAlert(Alert alert) {%
CompletionStage<Alert> stage = event%
.fireAsync(alert, executor);%
CDI2.0	非同期CDIイベント	
Comple0onStage.excep0onallyによる例外ハンドリング	
@ApplicationScoped%
publilc class AlertService {%
%
@Inject Event<Alert> event;%
@Resource ManagedExecutor executor;%
%
public void handleAlert(Alert alert) {%
CompletionStage<Alert> stage = event%
.fireAsync(alert, executor)%
.exceptionally(ex -> {%
// observer exception logging%
Arrays.stream(ex.getSuppressed())%
.forEach(e -> System.err.println(e));%
return null;%
}); %
CDI2.0	非同期CDIイベント	
CDI2.0より非同期実行に対応	
CDI1.2		
(Java	EE	7)	
CDI2.0	
(Java	EE	8)	
プラグイン	
(型依存の分離)	
非同期実行	
(実行タイミングの分離)	
○	 ○	
○
CDI2.0	非同期CDIイベント	
@MDBとCDI非同期イベント	
CDI1.2		
(Java	EE	7)	
CDI2.0	
(Java	EE	8)	
JMS	
プラグイン	
(型依存の分離)	
非同期実行	
(実行タイミングの分離)	
メッセージ永続化	
Observerの	
別マシン実行	
○	 ○	
○	
○	
○	
○	
○
CDI1.2		
(Java	EE	7)	
CDI2.0	
(Java	EE	8)	
JMS	
プラグイン	
(型依存の分離)	
非同期実行	
(実行タイミングの分離)	
メッセージ永続化	
Observerの	
別マシン実行	
CDI2.0	非同期CDIイベント	
@MDBとCDI非同期イベント	
○	 ○	
○	
○	
○	
○	
○	
【JMSに付いてくる検討項目】	
XAするならクラッシュリカバリ手順は?	
ポイズンメッセージ対策は?	
メッセージ永続化先は?ファイル or	DB?
CDI2.0	非同期CDIイベント	
@MDBとCDI非同期イベント	
CDI1.2		
(Java	EE	7)	
CDI2.0	
(Java	EE	8)	
JMS	
プラグイン	
(型依存の分離)	
非同期実行	
(実行タイミングの分離)	
メッセージ永続化	
Observerの	
別マシン実行	
考えるべき	
タスクの多さ	
○	 ○	
○	
○	
○	
○	
○	
△
CDI2.0	非同期CDIイベント	
CDI非同期イベントが適するケース	
•  順序性,	依存性のない処理の並列実行	
•  例外時のCDI管理Bean状態ロールバック	
•  トランザクション中に変更したステートを元に戻す	
•  メッセージ永続化が不要	
•  例:	朝からリクエスト時点までの業務統計レポート生成	
•  障害復旧後に永続メッセージから実行しても、既に陳腐化
CDI2.0	#2	
仕様をサブセットに分割
CDI2.0	仕様をサブセットに分割	
CDI	Lite	軽量なサブセットの抽出	
•  CDIを	Java	EE	以外の世界で使ってもらいたい	
•  Android,	組込みデバイス	
•  現状のCDI仕様はJava	EE環境を前提	
•  プロキシベースを前提としない軽量実装	
•  Annota0on	Processingによるコンパイル時依存性解決	
			(Androidでよく使われるDaggerがモデル)	
•  省メモリ、低CPU使用率の実現
CDI2.0	仕様をサブセットに分割	
CDI	Lite	軽量なサブセットの抽出	
CDI	core	
•  DI	-	@Inject,	Qualifier	
•  @Produces	
•  Event	&	@Observes	
•  疑似スコープ	
				@Dependent,	@Singleton	
•  Programa0c	lookup	
•  Portable	Exten0on	
CDI	Java	SE	
•  Bootstraping	API	
•  Scope	in	Java	SE	@Applica0onScoped	
•  Packaging	&	deployment	
CDI	Java	EE	
•  Scope	in	Java	EE	
•  @SessionScoped	
•  @Conversa0onScoped	
•  EJBとの連携
CDI2.0	#3	
Java	SE	Support
public static void main(String ... args) {%
try (CDI<Object> cdi = CDI.getCDIProvider().initialize()) {%
Service service = cdi.select(Service.class).get();%
service.doSomething(); %
}%
}%
%
public class ServiceImpl implements Service {%
@Inject %
Repository repo;%
%
public void doSomething() {...}%
}%
CDI2.0	Java	SE	Support	
Java	SE	Bootstrap	API		
CDIコンテナ初期化	
InjectされたBeanの取得
CDI2.0	Java	SE	Support	
“仕様”として含める背景	
•  Java	EE	仕様間での整合性	
•  JAX-RS	,	JPAは Java	SE	でも利用可能な仕様設計	
•  Weld,	OpenWebBeansで既に実装されていた	
•  実装間で類似APIが複数存在するのはJava	EE思想に反する
CDI2.0	#4	
Java	SE	8	Alignment
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
public class InterceptorBuilder {%
// デプロイ時にCDIコンテナよりコールバック%
void afterBeanDiscovery(@Observes AfterBeanDiscovery event) {%
event.addInterceptor() // return InterceptorBuilder%
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
public class InterceptorBuilder {%
// デプロイ時にCDIコンテナよりコールバック%
void afterBeanDiscovery(@Observes AfterBeanDiscovery event) {%
event.addInterceptor()%
.intercept(InterceptionType.AROUND_INVOKE, this::log)%
%
%
%
%
Object log(InvocationContext ic) {%
// interceptor impl%
}%
}%
@AroundInvoke相当
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
public class InterceptorBuilder {%
// デプロイ時にCDIコンテナよりコールバック%
void afterBeanDiscovery(@Observes AfterBeanDiscovery event) {%
event.addInterceptor()%
.intercept(InterceptionType.AROUND_INVOKE, this::log)%
.priority(Priority.APPLICATION)%
.addBinding(Log.INSTANCE);%
}%
%
Object log(InvocationContext ic) {%
// interceptor impl%
}%
}%
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
public class InterceptorBuilder {%
// デプロイ時にCDIコンテナよるコールバック%
void afterBeanDiscovery(@Observes AfterBeanDiscovery event) {%
event.addInterceptor()%
.intercept(InterceptionType.AROUND_INVOKE, this::log)%
.priority(Priority.APPLICATION)%
.addBinding(Log.INSTANCE);%
}%
%
Object log(InvocationContext ic) {%
// interceptor impl%
}%
}%
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
event.addInterceptor()%
...%
.addBinding(Log.INSTANCE);%
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
event.addInterceptor()%
...%
.addBinding(Log.INSTANCE);%
@Log%
public void target() {...} 	
適用対象メソッドと繋ぐために、	
アノテーションの“インスタンス”を渡す必要がある
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
event.addInterceptor()%
...%
.addBinding(Log.INSTANCE);%
%
@Inherited%
@InterceptorBinding%
@Retention(RUNTIME)%
@Target({METHOD, TYPE})%
public @interface Log {}%
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
event.addInterceptor()%
...%
.addBinding(Log.INSTANCE);%
%
@Inherited%
@InterceptorBinding%
@Retention(RUNTIME)%
@Target({METHOD, TYPE})%
public @interface Log {%
class Literal extends AnnotationLiteral<Log> implements Log {%
private Literal() {}%
}%
final Log INSTANCE = new Literal();%
}%
CDIのAnnota0onLiteralクラスを継承して	
アノテーションの”インスタンス”を取得
CDI2.0	Java	SE	8	Alignment	
InterceptorBuilder:	ラムダ	or	メソッド参照によるインターセプタ	
event.addInterceptor()%
...%
.addBinding(Log.INSTANCE);%
%
@Inherited%
@InterceptorBinding%
@Retention(RUNTIME)%
@Target({METHOD, TYPE})%
public @interface Log {%
class Literal extends AnnotationLiteral<Log> implements Log {%
private Literal() {}%
}%
final Log INSTANCE = new Literal();%
}%
@Log%
public void target() {...} 	
Interceptor	Binding
CDI2.0	Java	SE	8	Alignment		
InterceptorBuilderのメリット	
•  1クラスで複数のインターセプタ定義が可能	
•  クラスが冗長に増えるのを防ぐ	
•  Java	EEの何でもアノテーション状態の改善	
•  Java	5	から:	アノテーションをスキャンしてコンテナ機能を付与	
•  Java	8	から:	ラムダを渡すとコンテナが機能付与
CDI2.0	ロードマップ	
スケジュール	
•  2015/6:	Early	DraZ	Review	1		
•  hkps://docs.jboss.org/cdi/spec/2.0.EDR1/cdi-spec.html	
•  2016/6:	Early	DraZ	Review	2	予定	
•  2016/12	〜	2017/1:	CDI2.0	Final	予定	
•  2017上半期	Java	EE	8	リリース 予定
本日のコンテンツ	
•  駆け足で振り返るCDI	
•  CDI2.0 	
•  CDI + α	
•  最後に
DI/AOPが標準化され、非同期イベントが入るのはわかった。	
でも、まだ Spring	より足りないのでは?
Spring	Framework	
@Autowired,	@Aspect%
CDI	(Java	EE)	
@Inject,	@Interceptor	DI/AOP	
プロパティ管理	
@Value,
@PropertySource%
Java起動引数による	
プロファイル切替	
@Profile
CDIは『材料』のみ提供して、	
自作が必要なユースケースも多い	
Spring	Framework	
@Autowired,	@Aspect%
CDI	(Java	EE)	
@Inject,	@Interceptor	DI/AOP	
プロパティ管理	
@Value,
@PropertySource%
@Producesによる要自作	
Java起動引数による	
プロファイル切替	
@Profile	 @Alternativeによる要自作
CDI2.0(2017年)に向けて議論中ではある	
Spring	Framework	
@Autowired,	@Aspect%
CDI	(Java	EE)	
@Inject,	@Interceptor	DI/AOP	
プロパティ管理	
@Value,
@PropertySource%
@Producesによる要自作	
Java起動引数による	
プロファイル切替	
@Profile	
CDI-504:	have	a	standard	CDI	annota0on	like	@ConfigProperty	from	deltapsike	
hkps://issues.jboss.org/browse/CDI-504	
CDI-539:	Support	for	'profile'	in	CDI	
hkps://issues.jboss.org/browse/CDI-539	
【Issue	CDI-504】	
@Alternativeによる要自作	
【Issue	CDI-539】	
・ その機能は本当に『CDI』か?	
				過去例:	
						@Transac0onalをCDIではなくJTAへ	
・ やはり	Configra0on	JSR	では?
CDI2.0(2017年)に向けて議論中ではある	
CDI	(Java	EE)	
@Inject,	@Interceptor	
プロパティ管理	
@Value,
@PropertySource%
@Producesによる要自作	
Java起動引数による	
プロファイル切替	
@Profile	
CDI-504:	have	a	standard	CDI	annota0on	like	@ConfigProperty	from	deltapsike	
hkps://issues.jboss.org/browse/CDI-504	
CDI-539:	Support	for	'profile'	in	CDI	
hkps://issues.jboss.org/browse/CDI-539	
【Issue	CDI-504】	
@Alternativeによる要自作	
【Issue	CDI-539】	
Spring	Framework	
@Autowired,	@Aspect%DI/AOP	
・ その機能は本当に『CDI』か?	
				過去例:	
						@Transac0onalをCDIではなくJTAへ	
・ やはり	Configra0on	JSR	では?	
2017年を待てない場合は	
Apache	Deltaspike
“あったらいいな”はDeltaspikeにある	
Spring	Framework	
@Autowired,	@Aspect%
CDI	(Java	EE)	
@Inject,	@Interceptor	DI/AOP	
プロパティ管理	
@Value,
@PropertySource%
org.apache.deltaspike.core.api.config.%
@ConfigProperty	
Java起動引数による	
プロファイル切替	
@Profile	
org.apache.deltaspike.core.api.projectstage	
ProjectStage%
Apache	Deltaspike
Apache	Deltaspike	
便利なCDI拡張ライブラリ		
•  CDIのPortable	Exten0onを活かしたライブラリ	
•  Seem3	+	My	Faces	CODI	+	α	を統合	
•  2014/6:	1.0.0	リリース (2016/4	現在	1.6.1が最新)
Apache	Deltaspike	#1	@ConfigProperty	
@ConfigPropertyによるパラメータ注入		
@ApplicationScoped%
public class RemoteConnector {%
%
@Inject%
@ConfigProperty(name="remotehost", defaultValue="localhost:8080")%
private String remotehost;%
...%
META-INF/apache-deltaspike.proper0es	
remotehost=192.168.1.2	
DeltaspikeによりInject	
デフォルトのプロパティファイル
Apache	Deltaspike	#1	@ConfigProperty	
任意のプロパティファイルの適用	
@Dependent%
public class MyAppFileConfig implements PropertyFileConfig {%
@Override%
public String getPropertyFileName() {%
return "META-INF/application.properties";%
}%
%
@Override%
public boolean isOptional() {%
return false;%
}%
}
Apache	Deltaspike	#1	@ConfigProperty	
環境変数による値の差し替え	
@Inject%
@ConfigProperty(name="remotehost”,defaultValue="localhost:8080")%
private String remotehost;%
【優先順位】	
1.  環境変数	
export	remotehost=192.168.1.2	
2.  システムプロパティ	
java	-Dremotehost=192.168.1.4	
3.  JNDI	
new InitialContext().bind(“remotehost”, “192.168.1.5”)	
4.  プロパティファイル
Apache	Deltaspike	#2	ProjectStage	
起動オプションで有効なBeanを切り替える	
Service	 Repository	
【development】	
H2		
【produc0on】	
PostgreSQL	
META-INF/persistence.xml%
<?xml version="1.0" encoding="UTF-8"?>%
<persistence>%
<persistence-unit name="h2”>...</persistence-unit>%
<persistence-unit name="PostgreSQL”>...</persistence-unit>%
</persistence>
Apache	Deltaspike	#2	ProjectStage	
起動オプションで有効なBeanを切り替える	
@ApplicationScoped%
public class Repository {%
@PersistenceContext(unitName = “h2 or PostgreSQL??”)%
private EntityManager em;%
...%
}
Apache	Deltaspike	#2	ProjectStage	
Development環境向けEn0tyManagerのBean定義	
@ApplicationScoped%
public class Repository {%
@PersistenceContext(unitName = “h2 or PostgreSQL??”)%
private EntityManager em;%
...%
} 	
@Exclude(exceptIfProjectStage = ProjectStage.Development.class)%
@ApplicationScoped%
public class DevEntityManagerProducer {%
@Produces%
@PersistenceContext(unitName = "h2")%
private EntityManager em; %
}
Apache	Deltaspike	#2	ProjectStage	
Development環境向けEn0tyManagerのBean定義	
@ApplicationScoped%
public class Repository {%
@Inject%
private EntityManager em;%
...%
} 	
@Exclude(exceptIfProjectStage = ProjectStage.Development.class)%
@ApplicationScoped%
public class DevEntityManagerProducer {%
@Produces%
@PersistenceContext(unitName = "h2")%
private EntityManager em; %
}
Apache	Deltaspike	#2	ProjectStage	
システムプロパティで有効プロファイルを指定	
@ApplicationScoped%
public class Repository {%
@Inject%
private EntityManager em;%
...%
} 	
@Exclude(exceptIfProjectStage = ProjectStage.Development.class)%
@ApplicationScoped%
public class DevEntityManagerProducer {%
@Produces%
@PersistenceContext(unitName = "h2")%
private EntityManager em; %
}	
java	-Dorg.apache.deltaspike.ProjectStage=Development	
Repository	 H2		
PostgreSQL
Apache	Deltaspike	#2	ProjectStage	
Produc0on向けも同様	
@ApplicationScoped%
public class Repository {%
@Inject%
private EntityManager em;%
...%
} 	
@Exclude(exceptIfProjectStage = ProjectStage.Production.class)%
@ApplicationScoped%
public class ProdEntityManagerProducer {%
@Produces%
@PersistenceContext(unitName = ”PostgreSQL")%
private EntityManager em; %
}	
Repository	 H2		
PostgreSQL
Apache	Deltaspike	#2	ProjectStage	
Produc0on向けも同様	
@ApplicationScoped%
public class Repository {%
@Inject%
private EntityManager em;%
...%
} 	
@Exclude(exceptIfProjectStage = ProjectStage.Production.class)%
@ApplicationScoped%
public class ProdEntityManagerProducer {%
@Produces%
@PersistenceContext(unitName = ”PostgreSQL")%
private EntityManager em; %
}	
Repository	 H2		
PostgreSQL	
java	-Dorg.apache.deltaspike.ProjectStage=Produc0on
Apache	Deltaspike	
@ConfigPropertyとProjectStage	
•  2つに共通するメリット	
•  環境変数やJavaシステムプロパティで振る舞いを変更	
•  テスト済warを『修正なし』で複数環境で動作させる	
開発環境	 ステージング環境	 商用環境	
AP	
Server	
DB	
myapp.war	
Simurator	
myapp.war	 myapp.war	
関連システム
本日のコンテンツ	
•  駆け足で振り返るCDI	
•  CDI2.0	
•  CDI + α	
•  最後に
CDI2.0	(Java	EE	8	/	2017)	
•  	CDI非同期イベント	
•  	仕様をサブセットに分割	
•  	Java	SE	Support	
•  	Java	SE	8	Alignment
CDI2.0をもっと知るには	
cdi-spec.org	/	JIRA	/	Weld3.0.0.Alpha	
•  ホームページ (CDI	spec	で検索)	
•  hkp://www.cdi-spec.org	
•  JIRA	
•  hkps://issues.jboss.org/projects/CDI	
•  CDI2.0	EarlyDraZReview	1	の参照実装	
•  Weld	3.0.0.Alpha16	hkp://weld.cdi-spec.org/news/2016/04/28/weld-300Alpha16/	
•  WildFly10に組込み可能なpatchもリリース
最後に	
CDI2.0 ドラフト仕様は今すぐWildFly10で動きます	
ぜひ触ってみてください!	
OracleとJavaは、Oracle	Corpora0on及びその子会社、関連会社の米国及びその他の国における登録商標です。	
文中の社名、商品名等は各社の商標または登録商標である場合があります。

Contenu connexe

Tendances

Tendances (20)

Jbatch実践入門 #jdt2015
Jbatch実践入門 #jdt2015Jbatch実践入門 #jdt2015
Jbatch実践入門 #jdt2015
 
Advanced database monitoring in modern java
Advanced database monitoring in modern javaAdvanced database monitoring in modern java
Advanced database monitoring in modern java
 
WildFly Swarm - Rightsize Your Java EE Apps
WildFly Swarm - Rightsize Your Java EE AppsWildFly Swarm - Rightsize Your Java EE Apps
WildFly Swarm - Rightsize Your Java EE Apps
 
20160215 04 java ee7徹底入門 jbatch
20160215 04 java ee7徹底入門 jbatch20160215 04 java ee7徹底入門 jbatch
20160215 04 java ee7徹底入門 jbatch
 
JavaOne 2015 JDK Update (Jigsaw) #j1jp
JavaOne 2015 JDK Update (Jigsaw) #j1jpJavaOne 2015 JDK Update (Jigsaw) #j1jp
JavaOne 2015 JDK Update (Jigsaw) #j1jp
 
Java EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 FallJava EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 Fall
 
WildFly Swarmではじめる「パーツとしてのJavaEE」
WildFly Swarmではじめる「パーツとしてのJavaEE」WildFly Swarmではじめる「パーツとしてのJavaEE」
WildFly Swarmではじめる「パーツとしてのJavaEE」
 
Java EE 8先取り!MVC 1.0入門 [EDR2対応版] 2015-10-10更新
Java EE 8先取り!MVC 1.0入門 [EDR2対応版] 2015-10-10更新Java EE 8先取り!MVC 1.0入門 [EDR2対応版] 2015-10-10更新
Java EE 8先取り!MVC 1.0入門 [EDR2対応版] 2015-10-10更新
 
Hello Java
Hello JavaHello Java
Hello Java
 
はまる!JPA(初学者向けライト版)
はまる!JPA(初学者向けライト版)はまる!JPA(初学者向けライト版)
はまる!JPA(初学者向けライト版)
 
JSR 352 “Batch Applications for the Java Platform”
JSR 352 “Batch Applications for the Java Platform”JSR 352 “Batch Applications for the Java Platform”
JSR 352 “Batch Applications for the Java Platform”
 
Javaで1から10まで書いた話(sanitized)
Javaで1から10まで書いた話(sanitized)Javaで1から10まで書いた話(sanitized)
Javaで1から10まで書いた話(sanitized)
 
Head toward Java 16 (Night Seminar Edition)
Head toward Java 16 (Night Seminar Edition)Head toward Java 16 (Night Seminar Edition)
Head toward Java 16 (Night Seminar Edition)
 
Java SE 再入門
Java SE 再入門Java SE 再入門
Java SE 再入門
 
Javaチョットデキルへの道〜JavaコアSDKに見る真似したいコード10選〜
Javaチョットデキルへの道〜JavaコアSDKに見る真似したいコード10選〜Javaチョットデキルへの道〜JavaコアSDKに見る真似したいコード10選〜
Javaチョットデキルへの道〜JavaコアSDKに見る真似したいコード10選〜
 
Migration Guide from Java 8 to Java 11 #jjug
Migration Guide from Java 8 to Java 11 #jjugMigration Guide from Java 8 to Java 11 #jjug
Migration Guide from Java 8 to Java 11 #jjug
 
クリスマスを支える俺たちとJava(JJUG CCC 2015 Spring AB4)
クリスマスを支える俺たちとJava(JJUG CCC 2015 Spring AB4)クリスマスを支える俺たちとJava(JJUG CCC 2015 Spring AB4)
クリスマスを支える俺たちとJava(JJUG CCC 2015 Spring AB4)
 
Java EE 再入門
Java EE 再入門Java EE 再入門
Java EE 再入門
 
Java仮想マシンの実装技術
Java仮想マシンの実装技術Java仮想マシンの実装技術
Java仮想マシンの実装技術
 
Spring3.1概要x di
Spring3.1概要x diSpring3.1概要x di
Spring3.1概要x di
 

Similaire à CDI2.0アップデート&クックブック #JavaDayTokyo #jdt2016_4c

Similaire à CDI2.0アップデート&クックブック #JavaDayTokyo #jdt2016_4c (20)

Java/Androidセキュアコーディング
Java/AndroidセキュアコーディングJava/Androidセキュアコーディング
Java/Androidセキュアコーディング
 
はじめてのCodeIgniter
はじめてのCodeIgniterはじめてのCodeIgniter
はじめてのCodeIgniter
 
OpenShift Ansbile 活用法 アプリケーションライフサイクルからみる導入効果
OpenShift Ansbile 活用法 アプリケーションライフサイクルからみる導入効果OpenShift Ansbile 活用法 アプリケーションライフサイクルからみる導入効果
OpenShift Ansbile 活用法 アプリケーションライフサイクルからみる導入効果
 
多分モダンなWebアプリ開発
多分モダンなWebアプリ開発多分モダンなWebアプリ開発
多分モダンなWebアプリ開発
 
JavaでWebサービスを作り続けるための戦略と戦術 JJUG-CCC-2018-Spring-g1
JavaでWebサービスを作り続けるための戦略と戦術 JJUG-CCC-2018-Spring-g1JavaでWebサービスを作り続けるための戦略と戦術 JJUG-CCC-2018-Spring-g1
JavaでWebサービスを作り続けるための戦略と戦術 JJUG-CCC-2018-Spring-g1
 
CodeIgniter 〜 2008年大躍進のPHPフレームワーク
CodeIgniter 〜 2008年大躍進のPHPフレームワークCodeIgniter 〜 2008年大躍進のPHPフレームワーク
CodeIgniter 〜 2008年大躍進のPHPフレームワーク
 
企業システムで使えるマイクロサービスの特長と実践 (Oracle Cloudウェビナーシリーズ: 2021年4月15日)
企業システムで使えるマイクロサービスの特長と実践 (Oracle Cloudウェビナーシリーズ: 2021年4月15日)企業システムで使えるマイクロサービスの特長と実践 (Oracle Cloudウェビナーシリーズ: 2021年4月15日)
企業システムで使えるマイクロサービスの特長と実践 (Oracle Cloudウェビナーシリーズ: 2021年4月15日)
 
DevOps with Dynatrace
DevOps with DynatraceDevOps with Dynatrace
DevOps with Dynatrace
 
JPAの基礎と現場で役立つ開発Tips
JPAの基礎と現場で役立つ開発TipsJPAの基礎と現場で役立つ開発Tips
JPAの基礎と現場で役立つ開発Tips
 
The Twelve-Factor (A|M)pp with C#
The Twelve-Factor (A|M)pp with C#The Twelve-Factor (A|M)pp with C#
The Twelve-Factor (A|M)pp with C#
 
Spring2概論@第1回JSUG勉強会
Spring2概論@第1回JSUG勉強会Spring2概論@第1回JSUG勉強会
Spring2概論@第1回JSUG勉強会
 
Java in the World of Container by David Buck
Java in the World of Container by David BuckJava in the World of Container by David Buck
Java in the World of Container by David Buck
 
Scalable Generator: Using Scala in SIer Business (ScalaMatsuri)
Scalable Generator: Using Scala in SIer Business (ScalaMatsuri)Scalable Generator: Using Scala in SIer Business (ScalaMatsuri)
Scalable Generator: Using Scala in SIer Business (ScalaMatsuri)
 
Jakarta CDI 4.0
Jakarta CDI 4.0Jakarta CDI 4.0
Jakarta CDI 4.0
 
Springでdao 20070413
Springでdao 20070413Springでdao 20070413
Springでdao 20070413
 
Code igniterでテスト駆動開発 資料作成中
Code igniterでテスト駆動開発 資料作成中Code igniterでテスト駆動開発 資料作成中
Code igniterでテスト駆動開発 資料作成中
 
マークアップ講座 04 jQuery - JavaScript
マークアップ講座 04 jQuery - JavaScriptマークアップ講座 04 jQuery - JavaScript
マークアップ講座 04 jQuery - JavaScript
 
AndroidでDIxAOP
AndroidでDIxAOPAndroidでDIxAOP
AndroidでDIxAOP
 
Net advantage 2012 volume2 最新情報 Windows Forms / ASP.NET 編
Net advantage 2012 volume2 最新情報 Windows Forms / ASP.NET 編Net advantage 2012 volume2 最新情報 Windows Forms / ASP.NET 編
Net advantage 2012 volume2 最新情報 Windows Forms / ASP.NET 編
 
iOS の動画アプリ開発に Xamarin を使ってみた @JXUG #2 East
iOS の動画アプリ開発に Xamarin を使ってみた @JXUG #2 EastiOS の動画アプリ開発に Xamarin を使ってみた @JXUG #2 East
iOS の動画アプリ開発に Xamarin を使ってみた @JXUG #2 East
 

Plus de Norito Agetsuma

プロになるためのJavaScript入門読書会 レジュメ
プロになるためのJavaScript入門読書会 レジュメプロになるためのJavaScript入門読書会 レジュメ
プロになるためのJavaScript入門読書会 レジュメ
Norito Agetsuma
 
SQLアンチパターン読書会 レジュメ
SQLアンチパターン読書会 レジュメSQLアンチパターン読書会 レジュメ
SQLアンチパターン読書会 レジュメ
Norito Agetsuma
 

Plus de Norito Agetsuma (9)

Quarkus入門
Quarkus入門Quarkus入門
Quarkus入門
 
Java EEを補完する仕様 MicroProfile
Java EEを補完する仕様 MicroProfileJava EEを補完する仕様 MicroProfile
Java EEを補完する仕様 MicroProfile
 
Tomcatの実装から学ぶクラスローダリーク #渋谷Java
Tomcatの実装から学ぶクラスローダリーク #渋谷JavaTomcatの実装から学ぶクラスローダリーク #渋谷Java
Tomcatの実装から学ぶクラスローダリーク #渋谷Java
 
Javaトラブルに備えよう #jjug_ccc #ccc_h2
Javaトラブルに備えよう #jjug_ccc #ccc_h2Javaトラブルに備えよう #jjug_ccc #ccc_h2
Javaトラブルに備えよう #jjug_ccc #ccc_h2
 
Unixカーネルの設計 7 プロセスの制御
Unixカーネルの設計 7 プロセスの制御Unixカーネルの設計 7 プロセスの制御
Unixカーネルの設計 7 プロセスの制御
 
JJUG 11月ナイトセミナー CDIをはじめよう
JJUG 11月ナイトセミナー CDIをはじめようJJUG 11月ナイトセミナー CDIをはじめよう
JJUG 11月ナイトセミナー CDIをはじめよう
 
AeroGear & Java EE 7 で簡単プッシュ
AeroGear & Java EE 7 で簡単プッシュAeroGear & Java EE 7 で簡単プッシュ
AeroGear & Java EE 7 で簡単プッシュ
 
プロになるためのJavaScript入門読書会 レジュメ
プロになるためのJavaScript入門読書会 レジュメプロになるためのJavaScript入門読書会 レジュメ
プロになるためのJavaScript入門読書会 レジュメ
 
SQLアンチパターン読書会 レジュメ
SQLアンチパターン読書会 レジュメSQLアンチパターン読書会 レジュメ
SQLアンチパターン読書会 レジュメ
 

CDI2.0アップデート&クックブック #JavaDayTokyo #jdt2016_4c