SlideShare a Scribd company logo
1 of 168
Download to read offline
Reactive Webアプリケーション
- そしてSpring 5へ
Toshiaki Maki (@making)
JJUG CCC 2015 Fall
2015-11-30 #jjug_ccc
#ccc_ef3
聞いたことあります?
• Reactive Programming?
• Reactive Manifest?
• Reactive Streams?
• Reactive Extensions?
• Reactive ... ?
• Reactiveが重要視されてきた背景
• Reactive Streams
• Reactive Extensions
• Spring 5
今日話すこと
Reactive
Extensions(Rx)
Reactive
Programming
Reactive
Streams
Reactor
RxJava
Spring 5
プロラミング
パラダイム
仕様(?)
今日話すこと
実装
ライブラリ
Spring
Framework
元ネタ
http://www.slideshare.net/SpringCentral/reactive-web-applications-53170985
http://www.slideshare.net/SpringCentral/introduction-to-reactive-programming
Reactiveが重要視され
てきた背景
Amdalの法則
https://en.wikipedia.org/wiki/Amdahl%27s_law
Amdalの法則
https://en.wikipedia.org/wiki/Amdahl%27s_law
プログラムの並列化による速度の向上は、
プログラムの逐次処理部分によって制限される
Amdalの法則
https://en.wikipedia.org/wiki/Amdahl%27s_law
プログラムの並列化による速度の向上は、
プログラムの逐次処理部分によって制限される
プログラム中の
並列実行可能部分が50%
だと、いくら並列度を増や
しても2倍の性能向上し
か見込めない
スケールアウト戦略
• メモリばかり消費してCPUに空き…
✦ 大量のスレッドプール
✦ブロッキングI/O
ブロッキングコードを
書いていては
ハードにいくら金をかけても
性能向上に限界がある
Blocking is evil
• ブロッキングコードは並列化の妨げ
• 2大ブロッキング
• リクエストの受信待ち/レスポンス
の送信待ち
• DBクエリの結果待ち
Blocking is evil
• ブロッキングコードは並列化の妨げ
• 2大ブロッキング
• リクエストの受信待ち/レスポンス
の送信待ち
• DBクエリの結果待ち
InputStream
OutputStream
JDBC
• IoT
• マイクロサービス
今後のトレンド
• IoT
• マイクロサービス
低速で膨大な
リクエスト
が予想される
今後のトレンド
• IoT
• マイクロサービス
低速で膨大な
リクエスト
が予想される
今後のトレンド
Blocking == 💴
Non-Blocking!
• 命令型ではなくリスナー/コールバックス
タイル
• スレッド数を少なく
• →省メモリ
• →コンテキストスイッチを減らす
• →CPUを有効活用
Reactiveプログラミング
• 命令型と異なるプログラミングパラダイム
• 連続的なデータをイベントハンドラで処理する
• データフロー(データ同士の関係性)に着目した
イベントドリブンなプログラミング
Reactiveプログラミング
• 命令型と異なるプログラミングパラダイム
• 連続的なデータをイベントハンドラで処理する
• データフロー(データ同士の関係性)に着目した
イベントドリブンなプログラミング
ノンブロッキングコードを書く
のに向いている
最も身近なReactiveプログラミング?
最も身近なReactiveプログラミング?
最も身近なReactiveプログラミング?
最も身近なReactiveプログラミング?
最も身近なReactiveプログラミング?
A, Bの変更に伴い
Cも変わる
データフロー
A
B 2
+ C
A, Bの変更に伴い
Cも変わるhttps://speakerdeck.com/okapies/reactive-streams-ru-men-number-jjug
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
イベントストリーム
x2
+
1  2      4      3
9    6    8    6    5    9
8      4      2  64      2      1  3
A
B
C
命令型
int A = 3;
int B = 3;
int C = A + B * 2; // 9
B = 1;
A, Bが変更されても
Cは変わらない
JavaFXの場合
@FXML

Spinner<Integer> valueA;

@FXML

Spinner<Integer> valueB;

@FXML

Label valueC;
private void bind() {

IntegerProperty a = new SimpleIntegerProperty(0);

IntegerProperty b = new SimpleIntegerProperty(0);

NumberBinding c = a.add(b.multiply(2)); // c = a + 2 * b

a.bind(this.valueA.valueProperty());

b.bind(this.valueB.valueProperty());

valueC.textProperty().bind(c.asString());

}
http://aoe-tk.hatenablog.com/entry/2015/07/12/173402
A, Bの変更に伴い
Cも変わる
Reactive Webアプリケーション
Repository
DBService
Controller
Reactive Webアプリケーション
Repository
DBService
Controller
Reactive Webアプリケーション
Repository
DBService
Controller
Blocking Blocking
Reactive Webアプリケーション
Repository
DBService
Controller
Blocking BlockingBlocking
他サービス呼び出し
Reactive Streams
Reactive Streams
• http://www.reactive-streams.org/
• 非同期ストリームの標準仕様
• BackPressure付き
Reactive Streamsの動機
1. 技術面: データを送り側の勢いが受け
取り側の処理速度より速い場合に、デー
タが れることを防ぎたい
(BackPressure)
2. 開発面: 似たような機能(API)を持つ製
品群の相互互換性を持たせたい
関わっている会社
• Typesafe
• Pivotal
• Netflix
• RedHat
• など
関わっている会社
• Typesafe ... Akka Streams
• Pivotal ... Reactor
• Netflix ... RxJava
• RedHat ... Vert.x
• など
Reactive Streamsが提供するもの
• 4つのインターフェース
• 仕様ドキュメント
• TCK (仕様をテストするJUnitの親クラス)
public interface Publisher<T> {
public void subscribe(Subscriber<? super T> s);
}
public interface Subscription {
public void request(long n);
public void cancel();
}
public interface Subscriber<T> {
public void onSubscribe(Subscription s);
public void onNext(T t);
public void onError(Throwable t);
public void onComplete();
}
public interface Processor<T, R> extends
Publisher<T>, Subscriber<R> {}
org.reactivestreams
public interface Publisher<T> {
public void subscribe(Subscriber<? super T> s);
}
public interface Subscription {
public void request(long n);
public void cancel();
}
public interface Subscriber<T> {
public void onSubscribe(Subscription s);
public void onNext(T t);
public void onError(Throwable t);
public void onComplete();
}
public interface Processor<T, R> extends
Publisher<T>, Subscriber<R> {}
org.reactivestreams
BackPressure
呼び出し順
onSubscribe onNext* (onError | onComplete)?
Subscription SubscriberPublisher Application
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
onNext(●)
onNext(●)
onComplete()
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
onNext(●)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
onNext(●)
onNext(●)
onNext(●)
onNext(●)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(Long.MAX_VALUE)
onNext(●)
onNext(●)
onNext(●)
onNext(●)
onNext(●)
onComplete()
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)💣
💥
Subscription
subscribe(Subscriber)
SubscriberPublisher Application
onSubscribe(Subscription)
request(1)
onNext(●)
request(2)
onNext(●)
onNext(●)
request(4)
onError(Throwable)
💣
💥
RxJavaからinspired
RxJava Reactive Streams
Observable<T> Publisher<T>
Observer<T> Subscriber<T>
Subscription Subscription
Non BlockingなAPI
• TやList<T>の代わりにPublisher<T>を返す
Blocking Non Blocking
User
get(String name)
Publisher<User>
get(String name)
List<User>
allFriends(User user)
Publisher<User>
allFriends(User user)
実装例 (Publisher)
public class IntPublisher implements Publisher<Integer> {

@Override

public void subscribe(Subscriber<? super Integer> s) {

s.onSubscribe(new Subscription() {

Iterator<Integer> it = IntStream.range(0, 10)
.boxed().iterator();

@Override

public void request(long n) {

for (int i = 0; i < n; i++) {

if (it.hasNext()) {

s.onNext(it.next());

} else {

s.onComplete();

break;

}}}

@Override

public void cancel() {}

});}}
実装例 (Subscriber)public class IntSubscriber implements Subscriber<Integer> {

Subscription subscription;

int req = 1; // AtomicIntegerにすべき

@Override public void onSubscribe(Subscription s) {

subscription = s; s.request(req);

}

@Override public void onNext(Integer integer) {
System.out.println("Next -> " + integer);

if (--req == 0) {

req = new Random().nextInt(10) + 1;

subscription.request(req);
}

}

@Override public void onError(Throwable t) { /**/ }

@Override public void onComplete() {
System.out.println("Complete!");

}

}

使用例
Publisher<Integer> publisher = new IntPublisher();
Subscriber<Integer> subscriber = new IntSubscriber();
publisher.subscribe(subscriber);
// Next -> 1
// Next -> 2
// Next -> 3
// Next -> 4
// Next -> 5
// Next -> 6
// Next -> 7
// Next -> 8
// Next -> 9
// Next -> 10
// Complete!
使用例
Publisher<Integer> publisher = new IntPublisher();
Subscriber<Integer> subscriber = new IntSubscriber();
publisher.subscribe(subscriber);
// Next -> 1
// Next -> 2
// Next -> 3
// Next -> 4
// Next -> 5
// Next -> 6
// Next -> 7
// Next -> 8
// Next -> 9
// Next -> 10
// Complete!
IntPublisher/IntSubscriberは
インターフェースを実装しているだけ
で、実は仕様を満たしていない
(TCKを通らない)
Hot / Cold
• Hot Stream
• ずっと続いていて途中から見はじめるもの
• 株価情報、タイムライン、マウスイベント、タイマー
イベント、WebSocket、Server-Sent Events、メッ
セージキュー
• Cold Stream
• 再現可能で、最初から最後まで見れるもの
• 配列・リスト、ファイル、データベース、計算結果
(Future)
Reactive Streamsの仕様
• Subscriberは非同期でも同期でも
よい。ただし、ノンブロッキングで
ないといけない
実装プロダクト(フレームワーク)
• Reactor (Pivotal)
• RxJava (Netflix)
• Akka Streams (Typesafe)
• Vert.x (Redhat)
• Ratpack
• Quasar
http://www.reactive-streams.org/announce-1.0.0
実装データアクセスライブラリ
• MongoDB (公式)
• Apache Kafka
• Rabbit MQ (Scalaのみ)
• Slick3 (Scala)
• CouchDB (RxJava only)
• PostgreSQL (RxJava only、開発中?)
• Spark (検討中? SPARK-10420)
• など
MongoDB
• http://mongodb.github.io/mongo-java-driver-reactivestreams/
• MongoDB公式でReactive Streams API
がサポートされている
• チュートリアルがあるのでわかりやすい
MongoDB
MongoClient client = MongoClients.create(

"mongodb://localhost");

MongoDatabase db = client.getDatabase("mydb");

MongoCollection<Document> collection =
db.getCollection("test");
// Insert
Document doc = new Document("message", "Hello!");

Publisher<Success> insert = collection.insertOne(doc);

insert.subscribe(new PrintSubscriber<>("result=%s"));
// Select
Publisher<Document> docs = collection.find();

docs.subscribe(new PrintDocumentSubscriber());
MongoDB
// Bulk Operation
PrintSubscriber<BulkWriteResult> subscriber
= new PrintSubscriber<>("Bulk write results: %s");

collection.bulkWrite(Arrays.asList(

new InsertOneModel<>(new Document("_id", 4)),

new InsertOneModel<>(new Document("_id", 5)),

new InsertOneModel<>(new Document("_id", 6)),

new UpdateOneModel<>(new Document("_id", 1),
new Document("$set", new Document("x", 2))),

new DeleteOneModel<>(new Document("_id", 2)),

new ReplaceOneModel<>(new Document("_id", 3),
new Document("_id", 3).append("x",4))))
.subscribe(subscriber);
Apache Kafka
• https://github.com/softwaremill/reactive-kafka
• Scalaで実装されている。Java用API
も用意されている。
Apache Kafka
ReactiveKafka kafka = new ReactiveKafka();

ActorSystem system =
ActorSystem.create("ReactiveKafka");
Publisher<MessageAndMetadata<byte[], String>> topicA
= kafka.consume(new PropertiesBuilder.Consumer(
broker, zk, "topicA","group", decoder)
.build(), system);
topicA.subscribe(subscriber);
PostgreSQL
• https://github.com/alaisi/postgres-async-
driver
• https://github.com/mauricio/postgresql-async
PostgreSQL
Db db = new ConnectionPoolBuilder()
.hostname("localhost").port(5432).database("demo")
.username("postgres").password("")
.poolSize(20).build();


// RxJava's Observable
Observable<Row> result =
db.queryRows("select id,value from demo");
result.subscribe(...);
// to Reactive Streams
Publisher<Row> publisher =
RxReactiveStreams.toPublisher(result);
publisher.subscribe(...);
Publisher単体だと使いにくい
• Publisherはただのコールバック
• map、flatMap、merge、filer、take、zip
といっった合成(compose)や変換(transform)
のためのAPIがない → コールバック地獄に
• Publisherはインターフェースでしかないので
実装ライブラリ側で便利なAPIを提供可能。
コールバック地獄
• もっと命令的に書きたい
• ComposableなAPIが欲しい
(Reactive Streamsの範疇外)
Reactive Extensions
Reactive Extensions(Rx)
• 元々はMicrosoftのでErik Meijerによっ
て.NET(LINQ)向け開発されたライブラリ
• Observerパターンでイベントストリームを扱う
• イベントストリームを操作(変換、フィルタ、合成
など)する豊富なAPI群
• 多言語対応(Java, JavaScript, .NET, Swiftなど)
http://reactivex.io/
map
flatMap
filter
take
merge
zip
combileLatest
buffer
RxJava
• Netflix社が開発したRxのJava版
• Observable/Observer
• Observableに対して豊富なOperation APIを提供
Observable.just('a', 'b', 'c')
.take(2)
.map(Character::toUpperCase)
.consume(System.out::print); // AB
RxJava
• バージョン1.0ではReactive Streamsをnativeサポー
トしていない。Publisher <-> Observableアダプ
ターが必要
• バージョン2.0でReactive Streams対応予定
// Publisher <-> Observable
Publisher<String> publisher =
RxReactiveStreams.toPublisher(observable);
Observable<String> observable =
RxReactiveStreams.toObservable(publisher);
Reactor
• Pivotal社が開発
• LMAX Disruptorの高性能なRing Bufferを使用している
• Spring Frameworkの一部の機能で使用されている
• Reactive Streamsの

Publisher + Composable API → reactor.rx.Stream
Streams.just('a', 'b', 'c')
.take(2)
.map(Character::toUpperCase)
.consume(System.out::print); // AB
Reactor Projectshttp://projectreactor.io/docs/reference/#_about_the_project
Reactive StreamsとReactor Streamsの関係
BroadCaster
Action
Stream
Processor
Subscriber Publisher
Consumer
Class
Interface
extends implements
Reactive Streams
Reactor
Promise
Reactor Streamsへの変換
import reactor.rx.Stream;
import reactor.rx.Streams;
// Streamの要素を直接指定(Cold)
Stream<String> stream = Streams.just("a", "b");
// T[]やIterable<T>からStream<T>への変換(Cold)
Stream<String> stream = Streams.from(value);
// Publisher<T>からStream<T>へ変換
Stream<String> stream = Streams.wrap(publisher);
// Subscription.request(Long.MAX_VALUE)相当
// consumeに渡すラムダ式がonNextで実行される
stream.consume(s -> System.out.println(s));
// Subscription.request(2)を繰り返す
stream.capacity(2)
.consume(s -> System.out.println(s));
// デバッグログ出力
stream.log()
.consume(s -> System.out.println(s));
Reactive Streamsの仕様を
簡単に満たすヘルパー
List<Integer> items = /* ... */;
Publisher<Integer> publisher =
PublisherFactory.forEach((subscriber) -> {
Iterator<Integer> iterator
= subscriber.context();
if (iterator.hasNext()) {
subscriber.onNext(iterator.next());
} else {
subscriber.onComplete();
}
}, subscriber -> items.iterator());
reactor.rx.Streamを使うことで
Reactive Streamsを
Reactive Extensionsで操作できる
Kafka + Reactorで足し算
Publisher<MessageAndMetadata<byte[], String>> topicA =
kafka.consume(new PropertiesBuilder.Consumer(
broker, zk, "a", "group", decoder)

.build(), system);

Publisher<MessageAndMetadata<byte[], String>> topicB =
kafka.consume(new PropertiesBuilder.Consumer(
broker, zk, "b", "group", decoder)

.build(), system);


Publisher<Integer> a = Streams.wrap(topicA)
.map(x -> Integer.valueOf(x.message()));

Publisher<Integer> bx2 = Streams.wrap(topicB)
.map(x -> Integer.valueOf(x.message()))
.map(x -> x * 2);


Streams.combineLatest(a, bx2, tpl -> tpl.getT1()+tpl.getT2())

.consume(c -> {

System.out.println("a + b * 2 = " + c);

});
Kafka + Reactorで足し算
$ echo '3' | kafkacat -P -t a -b localhost:9092
$ echo '3' | kafkacat -P -t b -b localhost:9092
$ echo '1' | kafkacat -P -t b -b localhost:9092
a + b * 2 = 5
a + b * 2 = 9
Reactorでコナミコマンド
// Create a "Hot" stream
Broadcaster<String> stream
= Broadcaster.create(Environment.get());
stream.filter(x -> x.length() == 1)
.buffer(10, 1) // 10イベント分を1つずらしでまとめる
.map(s ->
"↑".equals(s.get(0)) && "↑".equals(s.get(1)) &&
""".equals(s.get(2)) && """.equals(s.get(3)) &&
"←".equals(s.get(4)) && "#".equals(s.get(5)) &&
"←".equals(s.get(6)) && "#".equals(s.get(7)) &&
"A".equals(s.get(8)) && "B".equals(s.get(9)))

.consume(isKonami -> {

System.out.println(isKonami ? "Konami!" : "NG");

});
Reactorでコナミコマンド
stream.onNext("A");

stream.onNext("↑");

stream.onNext("↑");

stream.onNext(""");

stream.onNext(""");

stream.onNext("←");

stream.onNext("#");

stream.onNext("←");

stream.onNext("#");

stream.onNext("A");

stream.onNext("B");

stream.onNext("←");
NG
Konami!
NG
コナミコマンド
HotStreamをエミュレート
外部サービス呼び出し (Blocking)
public interface LinkedInService {
List<String> findUsers(String keyword);
LinkedInProfile getConnection(String id);
}
public interface TwitterService {
TwitterProfile getUserProfile(String id);
}
public interface FacebookService {
FacebookProfile getUserProfile(String id);
}
外部サービス呼び出し (NonBlocking)
public interface LinkedInService {
Stream<String> findUsers(String keyword);
Stream<LinkedInProfile> getConnection(String id);
}
public interface TwitterService {
Stream<TwitterProfile> getUserProfile(String id);
}
public interface FacebookService {
Stream<FacebookProfile> getUserProfile(String id);
}
flatMap
linkedInService.findUsers("JJUG")
.take(5)
.flatMap(userName ->

linkedInService.getConnections(userName)
.take(3)
.flatMap(connection -> {

String twitterId = connection.getTwitterId();

Publisher<TwitterProfile> twitterProfile =
twitterService.getUserProfile(twitterId);

String facebookId = connection.getFacebookId();

Publisher<FacebookProfile> facebookProfile =
facebookService.getUserProfile(facebookId);

return Streams.zip(twitterProfile, facebookProfile,
(tp, fp) -> new UserConnectionInfo(
userName, connection, tp, fp));

})
)
.subscribe(System.out::println);
http://www.slideshare.net/SpringCentral/introduction-to-reactive-programming/60
Reactor or RxJava ?
Reactor RxJava
• Reactive Streamsを
Nativeサポート
• Spring連携
• Reactive Extensions
のサブセット
• Reactive Exensionsを
フルセットでサポート
• 他言語対応
• Reactive Streamsはア
ダプター経由
Reactive Streamsのメリット
• 非同期サポートライブラリを作りやすい
Reactive Streamsのメリット
• 非同期サポートライブラリを作りやすい
• async-db-driver
• Publisher/Subscriberのみを使ったコアライブラリ
• async-db-driver-reactor
• ReactorのStreamにラップ
• async-db-driver-rxjava
• RxJavaのObservableにラップ
• ...
https://github.com/ReactiveX/RxJava/wiki/Reactive-Streams#recommended-approach
package com.example.db.driver;
import org.reactivestreams.Publisher;
public class Database {
public Publisher getValue(String key) { /* ... */ }
}
package com.example.db.driver.reactor;
public class Database {
public Stream getValue(String key) {
return Streams.wrap(coreDatabase.getValue(key));
}
}
package com.example.db.driver.rxjava;
public class Database {
public Observable getValue(String key) {
return RxReactiveStreams.toObservable(
coreDatabase.getValue(key));
}
}
RxJava用
Reactor用
Core API
すべてがPublisherで繋がる
Repository
DBService
ControllerPublisher Publisher Publisher
PublisherPublisherPublisher
すべてがPublisherで繋がる
Repository
DBService
ControllerPublisher Publisher Publisher
PublisherPublisherPublisher
すべてがPublisherで繋がる
Repository
DBService
ControllerPublisher Publisher Publisher
PublisherPublisherPublisher
ここ
は?
Spring 5
Spring 5
• Q4 2016
• JDK 9サポート
• Java 8がベースライン
• HTTP 2対応
• Reactive対応
• JUnit5対応
Spring 5
• Q4 2016
• JDK 9サポート
• Java 8がベースライン
• HTTP 2対応
• Reactive対応
• JUnit5対応
Java Webアプリケーション
のReactive対応?
• Servlet APIは至るところでBlocking
• InputStream/OutputStream
• getParameters/getParts
• sendError
• ...
昨今のNoBlocking対応
フレームワーク
• Play Framework
• Vert.x
• Ratpack
• Reactor Net
• RxNetty
脱Servlet API組
↓
Netty利用
Servletはダメな子なのか
Servletはダメな子なのか
• Servlet 3.0 … 非同期処理サポート
Servletはダメな子なのか
• Servlet 3.0 … 非同期処理サポート
• Servlet 3.1 … Non-Blocking APIサ
ポート
Servlet 3.0
非同期処理サポート
void doGet(req, res) {
OutputStream out = res.getOutputStream();
AsyncContext ctx = req.startAsync();
doAsyncREST(req).thenAccept(json -> {
out.write(json);
ctx.complete();
});
}
http://www.slideshare.net/SimoneBordet/servlet-31-async-io
Servlet 3.0
非同期処理サポート
void doGet(req, res) {
OutputStream out = res.getOutputStream();
AsyncContext ctx = req.startAsync();
doAsyncREST(req).thenAccept(json -> {
out.write(json); // Blocking!!
ctx.complete();
});
}
http://www.slideshare.net/SimoneBordet/servlet-31-async-io
Servlet 3.1
Non-Blocking APIサポート
• リクエストの読み込み/レスポンスの書き込みを
Non-Blockingに行うためのAPIが追加された
• 以下のシーンで効果的
• ファイルアップロード/ダウンロード
• 低速ネットワークからの大量アクセス(モバイル、IoT)
void doGet(req, res) {
OutputStream out = res.getOutputStream();
AsyncContext ctx = req.startAsync();
out.setWriteListener(new WriteListener() {
void onWritePossible() {
while (on.isReady()) {
// ...
ctx.complete();
}
}
});
}
http://www.slideshare.net/SimoneBordet/servlet-31-async-io
Hello Worldサーブレット
@WebServlet(urlPatterns = "/hello"
, asyncSupported = true)
public class HelloServlet extends HttpServlet {
@Override
public void service(HttpServletRequest req,
HttpServletResponse resp) {
AsyncContext ctx = req.startAsync(req, resp);
ServletInputStream input = req.getInputStream();
ReadListener readListener =
new ReadListenerImpl(input, resp, ctx);
input.setReadListener(readListener);
}
class ReadListenerImpl implements ReadListener {
// ...
private final StringBuilder sb = new StringBuilder();
public ReadListenerImpl(ServletInputStream input,
HttpServletResponse resp, AsyncContext ctx) {/* ... */}
public void onDataAvailable() throws IOException {
int len = 0; byte b[] = new byte[1024];
while (input.isReady() && !input.isFinished()
&& (len = input.read(b)) != -1) {
sb.append(new String(b, 0, len));
}
}
public void onAllDataRead() throws IOException {
ServletOutputStream output = resp.getOutputStream();
WriteListener writeListener =
new WriteListenerImpl(output, ctx);
output.setWriteListener(writeListener);
}
public void onError(Throwable th) {
ctx.complete(); th.printStackTrace();
}
}
class WriteListenerImpl implements WriteListener {
private final ServletOutputStream output;
private final AsyncContext ctx;
public WriteListenerImpl(ServletOutputStream output,
AsyncContext ctx) {
this.output = output;
this.ctx = ctx;
}
public void onWritePossible() throws IOException {
output.print("Hello World!");
output.flush();
ctx.complete();
}
public void onError(Throwable th) {
th.printStackTrace();
}
}
Block
Servlet
Servlet
ReadListener
WriteListener
Servlet
ReadListener
WriteListener
書くのが辛い
• Non-Blockingの方が5倍コード量が多い
• isReady, isFinishedの制御が難しい
• ついgetParameterするとBlock...
http://www.slideshare.net/SimoneBordet/servlet-31-async-io
Spring Reactive
• Spring 5のReactive対応向け実験プロジェクト
• 開発メンバー
• Rossen Stoyanchev (Spring MVC)
• Stephane Maldini (Reactor, Reactive Streams)
• Arjen Poutsma (MVCのREST対応, Spring WS)
• Sébastien Deleuze (MVCのScriptEngine対応)
• Brian Clozel (MVCの静的リソースハンドリング対応)
https://github.com/spring-projects/spring-reactive
Servlet31HttpHandlerAdapter
• HttpServlet実装
• ReadListener/WriteListenerを
Observerパターンで実装
• Reactive Streams(Publisher/
Subscriber)を使用
• ReadListener→Publisher
• WriteListener→Subscriber
Servlet31HttpHandlerAdapter
https://github.com/spring-projects/spring-reactive/tree/master/src/main/java/org/springframework/http/server/servlet31
Instead of ...
interface ServerHttpRequest extends HttpRequest {
InputStream getBody();
}
interface ServerHttpResponse extends HttpMessage {
OutputStream getBody();
}
Use Publisher
interface ReactiveServerHttpRequest extends HttpRequest {
Publisher<ByteBuffer> getBody();
}
interface ReactiveServerHttpResponse extends HttpMessage {
Publisher<Void> setBody(Publisher<ByteBuffer> pub);
}
Spring MVCのアーキテクチャ
Dispatcher
Servlet
<<IF>>
HandlerAdapter
<<IF>>
HandlerMapping
Handler
(Object)
フレームワーク アプリケーション
org.springframework.web.servletパッケージ
これまでの
Spring MVCのアーキテクチャ
Dispatcher
Servlet
RequestMapping
HandlerAdapter
RequestMapping
HandlerMapping
@RequestMapping
HttpMessageConverter
org.springframework.web.servlet.mvc.method.annotationパッケージ
これまでの
Spring MVCのアーキテクチャ
Dispatcher
Servlet
RequestMapping
HandlerAdapter
RequestMapping
HandlerMapping
@RequestMapping
HttpMessageConverter
org.springframework.web.servlet.mvc.method.annotationパッケージ
所謂、
Controllerクラス
これまでの
Spring Reactiveのアーキテクチャ
<<IF>>
HandlerAdapter
<<IF>>
HandlerMapping
Handler
(Object)
フレームワーク アプリケーション
org.springframework.web.reactiveパッケージ
Servlet31Http
HandlerAdapter
<<IF>>
Reactive
HttpHandeler
Servlet31Http
HandlerAdapter
RequestMapping
HandlerAdapter
RequestMapping
HandlerMapping
@RequsetMapping
Encoder/Decoder
Spring Reactiveのアーキテクチャ
org.springframework.web.reactive.method.annotationパッケージ
Dispatcher
Handler
RequestMapping
HandlerAdapter
RequestMapping
HandlerMapping
@RequsetMapping
Encoder/Decoder
Spring Reactiveのアーキテクチャ
org.springframework.web.reactive.method.annotationパッケージ
Servlet31Http
HandlerAdapter
Dispatcher
Handler
Spring MVCと同じプログラミングモデルで
アプリケーションを記述できる
Spring Reactiveのアプローチ
Reactor Net
ReactorHttpHanderAdapter
RxNetty
RxNettyHttpHandlerAdapter
Undertow
UndertowHttpHandlerAdapter
Servlet31Http
HandlerAdapter
ReactiveStreams
@Controller
Jetty
Tomcat
Publisher
ReactiveHttpHandeler
Spring Reactiveのアプローチ
Reactor Net
ReactorHttpHanderAdapter
RxNetty
RxNettyHttpHandlerAdapter
Undertow
UndertowHttpHandlerAdapter
Servlet31Http
HandlerAdapter
ReactiveStreams
@Controller
Jetty
Tomcat
Publisher
ReactiveHttpHandeler
Servletコンテナ以外の
選択肢もある
Spring MVCのController
@RequestMapping("/")
@ResponseBody
Person hello(@RequestBody Person req) {
// ...
}
これまでの
Spring ReactiveのController
@RequestMapping("/")
@ResponseBody
Publisher<Person> hello(
@RequestBody Publisher<Person> req) {
// ...
}
Reactive Webアプリケーション
Repository
DBService
ControllerPublisher Publisher Publisher
PublisherPublisherPublisher
Reactive Webアプリケーション
Repository
DBService
ControllerPublisher Publisher Publisher
PublisherPublisherPublisher
SpringReactive
ReactiveExtensions
Reactive Streams
絶賛開発中
• Reactive Clientの実装
• Filter相当の実装
• Progressive HTML renderingの検討
Springは
Java EEの代替ではありません
落穂拾い
java.util.concurrent.Flow
• Reactive StreamsがJDK 9に入ります
• Flow.Publisher
• Flow.Subscriber
• Flow.Subscription
• Flow.Processor
• http://openjdk.java.net/jeps/266
• http://gee.cs.oswego.edu/dl/jsr166/dist/docs/java/util/concurrent/Flow.html
@author Doug Lea
j.u.c.Flow <-> Reactive Streams
• ブリッジ作成を検討中
• https://github.com/reactive-streams/reactive-streams-jvm/issues/294
import java.util.concurrent.Flow;
import org.reactivestreams.Publisher;
// j.u.c.Flow -> Reactive Streams
Publisher<T> toReactive(Flow.Publisher<>T);
// Reactive Streams -> j.u.c.Flow
Flow.Publisher<T> toFlow(Publisher<T>);
Servlet 4
• HTTP2とReactive Streams (Back Pressure)の
連携案
• JDK9にj.u.c.Flowが入ったため、御蔵入りの模様
https://java.net/projects/servlet-spec/lists/jsr369-experts/archive/2015-08/message/1
まとめ
• Blocking ==💴な時代がきている
• Non-Blocking化を助けるReactiveなパラダイム
• 非同期ストリーム標準 Reactive Streams
• イベントストリームの変換・合成 Reactive
Extensions
• Reactive Webアプリケーション向けフレームワー
クSpring ReactiveがSpring 5に向けて開発中
まとめ
• Blocking ==💴な時代がきている
• Non-Blocking化を助けるReactiveなパラダイム
• 非同期ストリーム標準 Reactive Streams
• イベントストリームの変換・合成 Reactive
Extensions
• Reactive Webアプリケーション向けフレームワー
クSpring ReactiveがSpring 5に向けて開発中
Spring Framework
を使っていきましょう

More Related Content

What's hot

ソフトウェアにおける 複雑さとは何なのか?
ソフトウェアにおける 複雑さとは何なのか?ソフトウェアにおける 複雑さとは何なのか?
ソフトウェアにおける 複雑さとは何なのか?Yoshitaka Kawashima
 
例外設計における大罪
例外設計における大罪例外設計における大罪
例外設計における大罪Takuto Wada
 
世界一わかりやすいClean Architecture
世界一わかりやすいClean Architecture世界一わかりやすいClean Architecture
世界一わかりやすいClean ArchitectureAtsushi Nakamura
 
さくっと理解するSpring bootの仕組み
さくっと理解するSpring bootの仕組みさくっと理解するSpring bootの仕組み
さくっと理解するSpring bootの仕組みTakeshi Ogawa
 
テスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるなテスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるなKentaro Matsui
 
5分で分かるgitのrefspec
5分で分かるgitのrefspec5分で分かるgitのrefspec
5分で分かるgitのrefspecikdysfm
 
詳説データベース輪読会: 分散合意その2
詳説データベース輪読会: 分散合意その2詳説データベース輪読会: 分散合意その2
詳説データベース輪読会: 分散合意その2Sho Nakazono
 
マイクロサービスバックエンドAPIのためのRESTとgRPC
マイクロサービスバックエンドAPIのためのRESTとgRPCマイクロサービスバックエンドAPIのためのRESTとgRPC
マイクロサービスバックエンドAPIのためのRESTとgRPCdisc99_
 
開発速度が速い #とは(LayerX社内資料)
開発速度が速い #とは(LayerX社内資料)開発速度が速い #とは(LayerX社内資料)
開発速度が速い #とは(LayerX社内資料)mosa siru
 
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理NTT DATA Technology & Innovation
 
.NET Core 3.0時代のメモリ管理
.NET Core 3.0時代のメモリ管理.NET Core 3.0時代のメモリ管理
.NET Core 3.0時代のメモリ管理KageShiron
 
マイクロにしすぎた結果がこれだよ!
マイクロにしすぎた結果がこれだよ!マイクロにしすぎた結果がこれだよ!
マイクロにしすぎた結果がこれだよ!mosa siru
 
こんなに使える!今どきのAPIドキュメンテーションツール
こんなに使える!今どきのAPIドキュメンテーションツールこんなに使える!今どきのAPIドキュメンテーションツール
こんなに使える!今どきのAPIドキュメンテーションツールdcubeio
 
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところ
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところ
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところY Watanabe
 
Spring 5に備えるリアクティブプログラミング入門
Spring 5に備えるリアクティブプログラミング入門Spring 5に備えるリアクティブプログラミング入門
Spring 5に備えるリアクティブプログラミング入門Takuya Iwatsuka
 
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24Shin Ohno
 
FlutterでGraphQLを扱う
FlutterでGraphQLを扱うFlutterでGraphQLを扱う
FlutterでGraphQLを扱うIgaHironobu
 
トランザクションの設計と進化
トランザクションの設計と進化トランザクションの設計と進化
トランザクションの設計と進化Kumazaki Hiroki
 
単なるキャッシュじゃないよ!?infinispanの紹介
単なるキャッシュじゃないよ!?infinispanの紹介単なるキャッシュじゃないよ!?infinispanの紹介
単なるキャッシュじゃないよ!?infinispanの紹介AdvancedTechNight
 

What's hot (20)

ソフトウェアにおける 複雑さとは何なのか?
ソフトウェアにおける 複雑さとは何なのか?ソフトウェアにおける 複雑さとは何なのか?
ソフトウェアにおける 複雑さとは何なのか?
 
例外設計における大罪
例外設計における大罪例外設計における大罪
例外設計における大罪
 
Docker Compose 徹底解説
Docker Compose 徹底解説Docker Compose 徹底解説
Docker Compose 徹底解説
 
世界一わかりやすいClean Architecture
世界一わかりやすいClean Architecture世界一わかりやすいClean Architecture
世界一わかりやすいClean Architecture
 
さくっと理解するSpring bootの仕組み
さくっと理解するSpring bootの仕組みさくっと理解するSpring bootの仕組み
さくっと理解するSpring bootの仕組み
 
テスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるなテスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるな
 
5分で分かるgitのrefspec
5分で分かるgitのrefspec5分で分かるgitのrefspec
5分で分かるgitのrefspec
 
詳説データベース輪読会: 分散合意その2
詳説データベース輪読会: 分散合意その2詳説データベース輪読会: 分散合意その2
詳説データベース輪読会: 分散合意その2
 
マイクロサービスバックエンドAPIのためのRESTとgRPC
マイクロサービスバックエンドAPIのためのRESTとgRPCマイクロサービスバックエンドAPIのためのRESTとgRPC
マイクロサービスバックエンドAPIのためのRESTとgRPC
 
開発速度が速い #とは(LayerX社内資料)
開発速度が速い #とは(LayerX社内資料)開発速度が速い #とは(LayerX社内資料)
開発速度が速い #とは(LayerX社内資料)
 
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理
え、まって。その並列分散処理、Kafkaのしくみでもできるの? Apache Kafkaの機能を利用した大規模ストリームデータの並列分散処理
 
.NET Core 3.0時代のメモリ管理
.NET Core 3.0時代のメモリ管理.NET Core 3.0時代のメモリ管理
.NET Core 3.0時代のメモリ管理
 
マイクロにしすぎた結果がこれだよ!
マイクロにしすぎた結果がこれだよ!マイクロにしすぎた結果がこれだよ!
マイクロにしすぎた結果がこれだよ!
 
こんなに使える!今どきのAPIドキュメンテーションツール
こんなに使える!今どきのAPIドキュメンテーションツールこんなに使える!今どきのAPIドキュメンテーションツール
こんなに使える!今どきのAPIドキュメンテーションツール
 
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところ
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところ
ツール比較しながら語る O/RマッパーとDBマイグレーションの実際のところ
 
Spring 5に備えるリアクティブプログラミング入門
Spring 5に備えるリアクティブプログラミング入門Spring 5に備えるリアクティブプログラミング入門
Spring 5に備えるリアクティブプログラミング入門
 
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24
Mercari JPのモノリスサービスをKubernetesに移行した話 PHP Conference 2022 9/24
 
FlutterでGraphQLを扱う
FlutterでGraphQLを扱うFlutterでGraphQLを扱う
FlutterでGraphQLを扱う
 
トランザクションの設計と進化
トランザクションの設計と進化トランザクションの設計と進化
トランザクションの設計と進化
 
単なるキャッシュじゃないよ!?infinispanの紹介
単なるキャッシュじゃないよ!?infinispanの紹介単なるキャッシュじゃないよ!?infinispanの紹介
単なるキャッシュじゃないよ!?infinispanの紹介
 

Viewers also liked

日本 Java ユーザーグループ JJUG CCC 2015 Fall by ソラコム 片山
日本 Java ユーザーグループ JJUG CCC 2015 Fall  by ソラコム 片山 日本 Java ユーザーグループ JJUG CCC 2015 Fall  by ソラコム 片山
日本 Java ユーザーグループ JJUG CCC 2015 Fall by ソラコム 片山 SORACOM,INC
 
Javaにおけるネイティブコード連携の各種手法の紹介
Javaにおけるネイティブコード連携の各種手法の紹介Javaにおけるネイティブコード連携の各種手法の紹介
Javaにおけるネイティブコード連携の各種手法の紹介khisano
 
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3irof N
 
【こっそり始める】Javaプログラマコーディングマイグレーション
【こっそり始める】Javaプログラマコーディングマイグレーション【こっそり始める】Javaプログラマコーディングマイグレーション
【こっそり始める】Javaプログラマコーディングマイグレーションyy yank
 
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点hishidama
 
プログラム初心者がWebサービスをリリースして運営するまで
プログラム初心者がWebサービスをリリースして運営するまでプログラム初心者がWebサービスをリリースして運営するまで
プログラム初心者がWebサービスをリリースして運営するまでTomoaki Iwasaki
 
Real world machine learning with Java for Fumankaitori.com
Real world machine learning with Java for Fumankaitori.comReal world machine learning with Java for Fumankaitori.com
Real world machine learning with Java for Fumankaitori.comMathieu Dumoulin
 
デバッガのしくみ(JDI)を学んでみよう
デバッガのしくみ(JDI)を学んでみようデバッガのしくみ(JDI)を学んでみよう
デバッガのしくみ(JDI)を学んでみようfukai_yas
 
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)sogdice
 
Java EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 FallJava EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 FallMasatoshi Tada
 
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景に
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景にマイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景に
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景にYusuke Suzuki
 
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-Takakiyo Tanaka
 
Unified JVM Logging
Unified JVM LoggingUnified JVM Logging
Unified JVM LoggingYuji Kubota
 
Project Jigsaw #kanjava
Project Jigsaw #kanjavaProject Jigsaw #kanjava
Project Jigsaw #kanjavaYuji Kubota
 
Spring Framework 5.0による Reactive Web Application #JavaDayTokyo
Spring Framework 5.0による Reactive Web Application #JavaDayTokyoSpring Framework 5.0による Reactive Web Application #JavaDayTokyo
Spring Framework 5.0による Reactive Web Application #JavaDayTokyoToshiaki Maki
 
Getting start Java EE Action-Based MVC with Thymeleaf
Getting start Java EE Action-Based MVC with ThymeleafGetting start Java EE Action-Based MVC with Thymeleaf
Getting start Java EE Action-Based MVC with ThymeleafMasatoshi Tada
 
Arachne Unweaved (JP)
Arachne Unweaved (JP)Arachne Unweaved (JP)
Arachne Unweaved (JP)Ikuru Kanuma
 
VMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VMVMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VMyy yank
 
Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1Kosuke Kida
 
Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.JustSystems Corporation
 

Viewers also liked (20)

日本 Java ユーザーグループ JJUG CCC 2015 Fall by ソラコム 片山
日本 Java ユーザーグループ JJUG CCC 2015 Fall  by ソラコム 片山 日本 Java ユーザーグループ JJUG CCC 2015 Fall  by ソラコム 片山
日本 Java ユーザーグループ JJUG CCC 2015 Fall by ソラコム 片山
 
Javaにおけるネイティブコード連携の各種手法の紹介
Javaにおけるネイティブコード連携の各種手法の紹介Javaにおけるネイティブコード連携の各種手法の紹介
Javaにおけるネイティブコード連携の各種手法の紹介
 
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3
よくある業務開発の自動化事情 #jjug_ccc #ccc_cd3
 
【こっそり始める】Javaプログラマコーディングマイグレーション
【こっそり始める】Javaプログラマコーディングマイグレーション【こっそり始める】Javaプログラマコーディングマイグレーション
【こっそり始める】Javaプログラマコーディングマイグレーション
 
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点
Java8 Stream APIとApache SparkとAsakusa Frameworkの類似点・相違点
 
プログラム初心者がWebサービスをリリースして運営するまで
プログラム初心者がWebサービスをリリースして運営するまでプログラム初心者がWebサービスをリリースして運営するまで
プログラム初心者がWebサービスをリリースして運営するまで
 
Real world machine learning with Java for Fumankaitori.com
Real world machine learning with Java for Fumankaitori.comReal world machine learning with Java for Fumankaitori.com
Real world machine learning with Java for Fumankaitori.com
 
デバッガのしくみ(JDI)を学んでみよう
デバッガのしくみ(JDI)を学んでみようデバッガのしくみ(JDI)を学んでみよう
デバッガのしくみ(JDI)を学んでみよう
 
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)
Java8移行から始めた技術的負債との戦い(jjug ccc 2015 fall)
 
Java EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 FallJava EEハンズオン資料 JJUG CCC 2015 Fall
Java EEハンズオン資料 JJUG CCC 2015 Fall
 
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景に
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景にマイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景に
マイクロサービスアーキテクチャ - アーキテクチャ設計の歴史を背景に
 
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-
タイムマシン採用:明日のエンタープライズJavaの世界を予想する -Java EE7/クラウド/Docker/etc.-
 
Unified JVM Logging
Unified JVM LoggingUnified JVM Logging
Unified JVM Logging
 
Project Jigsaw #kanjava
Project Jigsaw #kanjavaProject Jigsaw #kanjava
Project Jigsaw #kanjava
 
Spring Framework 5.0による Reactive Web Application #JavaDayTokyo
Spring Framework 5.0による Reactive Web Application #JavaDayTokyoSpring Framework 5.0による Reactive Web Application #JavaDayTokyo
Spring Framework 5.0による Reactive Web Application #JavaDayTokyo
 
Getting start Java EE Action-Based MVC with Thymeleaf
Getting start Java EE Action-Based MVC with ThymeleafGetting start Java EE Action-Based MVC with Thymeleaf
Getting start Java EE Action-Based MVC with Thymeleaf
 
Arachne Unweaved (JP)
Arachne Unweaved (JP)Arachne Unweaved (JP)
Arachne Unweaved (JP)
 
VMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VMVMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VM
 
Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1
 
Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.
 

Similar to Reactive Webアプリケーション - そしてSpring 5へ #jjug_ccc #ccc_ef3

jjugccc2018 app review postmortem
jjugccc2018 app review postmortemjjugccc2018 app review postmortem
jjugccc2018 app review postmortemtamtam180
 
Live Coding で学ぶ C# 7
Live Coding で学ぶ C# 7Live Coding で学ぶ C# 7
Live Coding で学ぶ C# 7Takaaki Suzuki
 
なぜリアクティブは重要か #ScalaMatsuri
なぜリアクティブは重要か #ScalaMatsuriなぜリアクティブは重要か #ScalaMatsuri
なぜリアクティブは重要か #ScalaMatsuriYuta Okamoto
 
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」Hiroyuki Ohnaka
 
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1Masaya Aoyama
 
Why Reactive Matters #ScalaMatsuri
Why Reactive Matters #ScalaMatsuriWhy Reactive Matters #ScalaMatsuri
Why Reactive Matters #ScalaMatsuriYuta Okamoto
 
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワル
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワルAndrosia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワル
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワルCODE BLUE
 
VSCodeで始めるAzure Static Web Apps開発
VSCodeで始めるAzure Static Web Apps開発VSCodeで始めるAzure Static Web Apps開発
VSCodeで始めるAzure Static Web Apps開発Yuta Matsumura
 
Struts2を始めよう!
Struts2を始めよう!Struts2を始めよう!
Struts2を始めよう!Shinpei Ohtani
 
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強Kiyoshi Ogawa
 
How to manage Cakephp @CakePHP_Fukuoka_2
How to manage Cakephp @CakePHP_Fukuoka_2 How to manage Cakephp @CakePHP_Fukuoka_2
How to manage Cakephp @CakePHP_Fukuoka_2 ichikaway
 
T69 c++cli ネイティブライブラリラッピング入門
T69 c++cli ネイティブライブラリラッピング入門T69 c++cli ネイティブライブラリラッピング入門
T69 c++cli ネイティブライブラリラッピング入門伸男 伊藤
 
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃん
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃんRetrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃん
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃんYukari Sakurai
 
Spring BootでHello Worldのその先へ
Spring BootでHello Worldのその先へSpring BootでHello Worldのその先へ
Spring BootでHello Worldのその先へMasatoshi Fujino
 

Similar to Reactive Webアプリケーション - そしてSpring 5へ #jjug_ccc #ccc_ef3 (20)

jjugccc2018 app review postmortem
jjugccc2018 app review postmortemjjugccc2018 app review postmortem
jjugccc2018 app review postmortem
 
Live Coding で学ぶ C# 7
Live Coding で学ぶ C# 7Live Coding で学ぶ C# 7
Live Coding で学ぶ C# 7
 
なぜリアクティブは重要か #ScalaMatsuri
なぜリアクティブは重要か #ScalaMatsuriなぜリアクティブは重要か #ScalaMatsuri
なぜリアクティブは重要か #ScalaMatsuri
 
Service Workerとの戦い ~ 実装編 ~ #scripty03
Service Workerとの戦い ~ 実装編 ~ #scripty03Service Workerとの戦い ~ 実装編 ~ #scripty03
Service Workerとの戦い ~ 実装編 ~ #scripty03
 
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」
JavaOne 2015 報告会 @ 東京 「About MVC 1.0 & JSON-P」
 
ReactiveSignalR
ReactiveSignalRReactiveSignalR
ReactiveSignalR
 
Rx java x retrofit
Rx java x retrofitRx java x retrofit
Rx java x retrofit
 
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1
ServiceMesh と仲間たち 〜Istio & Conduit & Linkerd〜 @Cloud Native Meetup Tokyo #1
 
Why Reactive Matters #ScalaMatsuri
Why Reactive Matters #ScalaMatsuriWhy Reactive Matters #ScalaMatsuri
Why Reactive Matters #ScalaMatsuri
 
Etnet2015.slide
Etnet2015.slideEtnet2015.slide
Etnet2015.slide
 
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワル
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワルAndrosia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワル
Androsia:一歩先のメモリ内Androidアプリケーションデータの保護 by サミット・アンワル
 
CQRS+ES on GCP
CQRS+ES on GCPCQRS+ES on GCP
CQRS+ES on GCP
 
Cubby 2008-09-06
Cubby 2008-09-06Cubby 2008-09-06
Cubby 2008-09-06
 
VSCodeで始めるAzure Static Web Apps開発
VSCodeで始めるAzure Static Web Apps開発VSCodeで始めるAzure Static Web Apps開発
VSCodeで始めるAzure Static Web Apps開発
 
Struts2を始めよう!
Struts2を始めよう!Struts2を始めよう!
Struts2を始めよう!
 
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強
STARC RTL設計スタイルガイドによるVerilog HDL並列記述の補強
 
How to manage Cakephp @CakePHP_Fukuoka_2
How to manage Cakephp @CakePHP_Fukuoka_2 How to manage Cakephp @CakePHP_Fukuoka_2
How to manage Cakephp @CakePHP_Fukuoka_2
 
T69 c++cli ネイティブライブラリラッピング入門
T69 c++cli ネイティブライブラリラッピング入門T69 c++cli ネイティブライブラリラッピング入門
T69 c++cli ネイティブライブラリラッピング入門
 
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃん
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃんRetrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃん
Retrofit2 &OkHttp 
でAndroidのHTTP通信が快適だにゃん
 
Spring BootでHello Worldのその先へ
Spring BootでHello Worldのその先へSpring BootでHello Worldのその先へ
Spring BootでHello Worldのその先へ
 

More from Toshiaki Maki

From Spring Boot 2.2 to Spring Boot 2.3 #jsug
From Spring Boot 2.2 to Spring Boot 2.3 #jsugFrom Spring Boot 2.2 to Spring Boot 2.3 #jsug
From Spring Boot 2.2 to Spring Boot 2.3 #jsugToshiaki Maki
 
Concourse x Spinnaker #concourse_tokyo
Concourse x Spinnaker #concourse_tokyoConcourse x Spinnaker #concourse_tokyo
Concourse x Spinnaker #concourse_tokyoToshiaki Maki
 
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1t
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1tServerless with Spring Cloud Function, Knative and riff #SpringOneTour #s1t
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1tToshiaki Maki
 
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1Toshiaki Maki
 
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1Toshiaki Maki
 
Spring Boot Actuator 2.0 & Micrometer
Spring Boot Actuator 2.0 & MicrometerSpring Boot Actuator 2.0 & Micrometer
Spring Boot Actuator 2.0 & MicrometerToshiaki Maki
 
Open Service Broker APIとKubernetes Service Catalog #k8sjp
Open Service Broker APIとKubernetes Service Catalog #k8sjpOpen Service Broker APIとKubernetes Service Catalog #k8sjp
Open Service Broker APIとKubernetes Service Catalog #k8sjpToshiaki Maki
 
Spring Cloud Function & Project riff #jsug
Spring Cloud Function & Project riff #jsugSpring Cloud Function & Project riff #jsug
Spring Cloud Function & Project riff #jsugToshiaki Maki
 
Introduction to Spring WebFlux #jsug #sf_a1
Introduction to Spring WebFlux #jsug #sf_a1Introduction to Spring WebFlux #jsug #sf_a1
Introduction to Spring WebFlux #jsug #sf_a1Toshiaki Maki
 
BOSH / CF Deployment in modern ways #cf_tokyo
BOSH / CF Deployment in modern ways #cf_tokyoBOSH / CF Deployment in modern ways #cf_tokyo
BOSH / CF Deployment in modern ways #cf_tokyoToshiaki Maki
 
Why PCF is the best platform for Spring Boot
Why PCF is the best platform for Spring BootWhy PCF is the best platform for Spring Boot
Why PCF is the best platform for Spring BootToshiaki Maki
 
Zipkin Components #zipkin_jp
Zipkin Components #zipkin_jpZipkin Components #zipkin_jp
Zipkin Components #zipkin_jpToshiaki Maki
 
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07Toshiaki Maki
 
実例で学ぶ、明日から使えるSpring Boot Tips #jsug
実例で学ぶ、明日から使えるSpring Boot Tips #jsug実例で学ぶ、明日から使えるSpring Boot Tips #jsug
実例で学ぶ、明日から使えるSpring Boot Tips #jsugToshiaki Maki
 
Spring ❤️ Kotlin #jjug
Spring ❤️ Kotlin #jjugSpring ❤️ Kotlin #jjug
Spring ❤️ Kotlin #jjugToshiaki Maki
 
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3Toshiaki Maki
 
Managing your Docker image continuously with Concourse CI
Managing your Docker image continuously with Concourse CIManaging your Docker image continuously with Concourse CI
Managing your Docker image continuously with Concourse CIToshiaki Maki
 
Data Microservices with Spring Cloud Stream, Task, and Data Flow #jsug #spri...
Data Microservices with Spring Cloud Stream, Task,  and Data Flow #jsug #spri...Data Microservices with Spring Cloud Stream, Task,  and Data Flow #jsug #spri...
Data Microservices with Spring Cloud Stream, Task, and Data Flow #jsug #spri...Toshiaki Maki
 
Short Lived Tasks in Cloud Foundry #cfdtokyo
Short Lived Tasks in Cloud Foundry #cfdtokyoShort Lived Tasks in Cloud Foundry #cfdtokyo
Short Lived Tasks in Cloud Foundry #cfdtokyoToshiaki Maki
 
今すぐ始めるCloud Foundry #hackt #hackt_k
今すぐ始めるCloud Foundry #hackt #hackt_k今すぐ始めるCloud Foundry #hackt #hackt_k
今すぐ始めるCloud Foundry #hackt #hackt_kToshiaki Maki
 

More from Toshiaki Maki (20)

From Spring Boot 2.2 to Spring Boot 2.3 #jsug
From Spring Boot 2.2 to Spring Boot 2.3 #jsugFrom Spring Boot 2.2 to Spring Boot 2.3 #jsug
From Spring Boot 2.2 to Spring Boot 2.3 #jsug
 
Concourse x Spinnaker #concourse_tokyo
Concourse x Spinnaker #concourse_tokyoConcourse x Spinnaker #concourse_tokyo
Concourse x Spinnaker #concourse_tokyo
 
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1t
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1tServerless with Spring Cloud Function, Knative and riff #SpringOneTour #s1t
Serverless with Spring Cloud Function, Knative and riff #SpringOneTour #s1t
 
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1
決済システムの内製化への旅 - SpringとPCFで作るクラウドネイティブなシステム開発 #jsug #sf_h1
 
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1
Spring Boot Actuator 2.0 & Micrometer #jjug_ccc #ccc_a1
 
Spring Boot Actuator 2.0 & Micrometer
Spring Boot Actuator 2.0 & MicrometerSpring Boot Actuator 2.0 & Micrometer
Spring Boot Actuator 2.0 & Micrometer
 
Open Service Broker APIとKubernetes Service Catalog #k8sjp
Open Service Broker APIとKubernetes Service Catalog #k8sjpOpen Service Broker APIとKubernetes Service Catalog #k8sjp
Open Service Broker APIとKubernetes Service Catalog #k8sjp
 
Spring Cloud Function & Project riff #jsug
Spring Cloud Function & Project riff #jsugSpring Cloud Function & Project riff #jsug
Spring Cloud Function & Project riff #jsug
 
Introduction to Spring WebFlux #jsug #sf_a1
Introduction to Spring WebFlux #jsug #sf_a1Introduction to Spring WebFlux #jsug #sf_a1
Introduction to Spring WebFlux #jsug #sf_a1
 
BOSH / CF Deployment in modern ways #cf_tokyo
BOSH / CF Deployment in modern ways #cf_tokyoBOSH / CF Deployment in modern ways #cf_tokyo
BOSH / CF Deployment in modern ways #cf_tokyo
 
Why PCF is the best platform for Spring Boot
Why PCF is the best platform for Spring BootWhy PCF is the best platform for Spring Boot
Why PCF is the best platform for Spring Boot
 
Zipkin Components #zipkin_jp
Zipkin Components #zipkin_jpZipkin Components #zipkin_jp
Zipkin Components #zipkin_jp
 
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07
マイクロサービスに必要な技術要素はすべてSpring Cloudにある #DO07
 
実例で学ぶ、明日から使えるSpring Boot Tips #jsug
実例で学ぶ、明日から使えるSpring Boot Tips #jsug実例で学ぶ、明日から使えるSpring Boot Tips #jsug
実例で学ぶ、明日から使えるSpring Boot Tips #jsug
 
Spring ❤️ Kotlin #jjug
Spring ❤️ Kotlin #jjugSpring ❤️ Kotlin #jjug
Spring ❤️ Kotlin #jjug
 
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3
Event Driven Microservices with Spring Cloud Stream #jjug_ccc #ccc_ab3
 
Managing your Docker image continuously with Concourse CI
Managing your Docker image continuously with Concourse CIManaging your Docker image continuously with Concourse CI
Managing your Docker image continuously with Concourse CI
 
Data Microservices with Spring Cloud Stream, Task, and Data Flow #jsug #spri...
Data Microservices with Spring Cloud Stream, Task,  and Data Flow #jsug #spri...Data Microservices with Spring Cloud Stream, Task,  and Data Flow #jsug #spri...
Data Microservices with Spring Cloud Stream, Task, and Data Flow #jsug #spri...
 
Short Lived Tasks in Cloud Foundry #cfdtokyo
Short Lived Tasks in Cloud Foundry #cfdtokyoShort Lived Tasks in Cloud Foundry #cfdtokyo
Short Lived Tasks in Cloud Foundry #cfdtokyo
 
今すぐ始めるCloud Foundry #hackt #hackt_k
今すぐ始めるCloud Foundry #hackt #hackt_k今すぐ始めるCloud Foundry #hackt #hackt_k
今すぐ始めるCloud Foundry #hackt #hackt_k
 

Reactive Webアプリケーション - そしてSpring 5へ #jjug_ccc #ccc_ef3