practical rxjava - jfokus · practical rxjava @couchbase @infoqfr @bbl_fr @simonbasle. the plan...

113
Practical RxJava

Upload: others

Post on 21-May-2020

13 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Practical RxJava

Page 2: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

@Couchbase @InfoQFR @bbl_fr

@SimonBasle

Page 3: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

the

Plan&

Goals

Page 4: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

RxJava101

Page 5: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

migrate a

Legacyapplication

RxJava101

Page 6: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

migrate a

Legacyapplication

learn

Operatorsof interest

RxJava101

Page 7: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

migrate a

Legacyapplication

learn

Operatorsof interest

9 steps+

Q&A

RxJava101

Page 8: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Why?

Page 9: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Blocking it’s Evil, m’kay?

Page 10: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Blocking it’s Evil, m’kay?

Page 11: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

we need

asynchronous code

Page 12: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

we need reactive

asynchronous code

Page 13: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

we needparallelisable

asynchronous code

Page 14: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

we need composable

asynchronous code

Page 15: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

we need readable

asynchronous code

Page 16: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

but

how?

Page 17: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Futures<T>?Callbacks?

Page 18: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Futures<T>?Callbacks?too easy to block

(get)

complex beyond 1 level of composition

no composition

have you heared of Callback Hell?

Page 19: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

DocumentService.find("userId", new Callback<List<Document>>() {public void onSuccess(List<Document> result) {

final List<String> jsonList = new ArrayList<String>(10);int taken = 0;for (Document doc : result) {

if (taken >= 10)break;

if (!doc.isStarred())continue;

taken++;final CountDownLatch rendezVous = new CountDownLatch(3);final JsonObject jsonBuffer = new JsonObject();jsonBuffer.appendInt("id", doc.getId());jsonBuffer.append("text", doc.getText());CommentService.findForDoc(doc, new Callback<List<Comment>>() {

public void onSuccess(List<Comment> comments) {final JsonObject commentArray = JsonObject.createArray();CountDownLatch userLatch = new CountDownLatch(comments.size());for (Comment c : comments) {

JsonObject cj = new JsonObject();cj.append("content", c.getText());cj.append("date", c.getDate());UserService.find(c.getUserId(), new Callback<User>() {

public void onSuccess(User user) {cj.append("author", user.getName());cj.append("nickname", user.getLogin());cj.append("email", user.getEmail());// …

Futures<T>?Callbacks?too easy to block

(get)

complex beyond 1 level of composition

no composition

have you heared of Callback Hell?

Page 20: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

RxJava101

Page 21: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

RxJava101

Page 22: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

NetflixOpenSource

Page 23: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

dual ofIterable - Iterator

Page 24: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Iterable - Iteratorbecomes

Observable - Observer

Page 25: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Iterable - Iteratorbecomes

Observable - Observer

“Pull”

“Push”

Page 26: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

compose

Page 27: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

compose asynchronous programs

based on events

Page 28: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

compose asynchronous programs

based on eventsusing observable sequences

Page 29: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

the Reactive Manifestoreactivemanifesto.org

Page 30: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

reactive-streams.org

standardize on the jvm

Page 31: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

reactive-streams.org

standardize on the jvmakka - reactor - rxjava

Page 32: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Show Mehow it works !

Page 33: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

interface Observer<T>

Page 34: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

interface Observer<T>onNext(T data)

Page 35: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

interface Observer<T>onNext(T data)

onCompleted()

Page 36: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

interface Observer<T>onNext(T data) onCompleted()

onError(Throwable t)

Page 37: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

interface Observer<T>onNext(T data) onCompleted()

onError(Throwable t)

Page 38: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Observable<T>

Page 39: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Observable<T>compose & chain a stream

Page 40: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Observable<T>subscribe an Observer<T>

Page 41: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

so much Choice, you’ll see!

Page 42: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

still lost…time to practice

Page 43: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

The Legacy app

Page 44: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Wow

pool API?

Much Legacy!

Page 45: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Doge Mining Pool Client (UI?)

Rest Controller Rest Controller Rest Controller Rest Controller

Service Service Service

External API External API External APIDB

LEGACY

Page 46: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Doge Mining Pool Client (UI?)

Rest Controller Rest Controller Rest Controller Rest Controller

Service Service Service

External API External API External APIDB

Page 47: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Doge Mining Pool Client (UI?)

Rest Controller Rest Controller Rest Controller Rest Controller

Service Service Service

External API External API External APIDB

Page 48: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

simple Creation1

Page 49: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

● AdminService● CoinService● HashrateService● PoolService

Page 50: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● Observable.just● Observable.from● Observable.create (try it on PoolService.connect)

● map

Page 51: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● Observable.just● Observable.from● Observable.create

● map

Page 52: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

But now it doesn’t compile

how to adapt the Controllers?

Page 53: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Naively

Block on an Observable

take(n) vs single() vs first()

xxxOrDefault(t), toList()

Page 54: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Take

Page 55: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Single

Page 56: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

SingleOrDefault

Page 57: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Transform2

Page 58: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

● PoolRateService

Page 59: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● flatMap● reduce

Page 60: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

flatMap

Page 61: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

reduce

Page 62: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Filter3

Page 63: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

● UserService○ findAll for now naively adapted (Observable.from)○ compose on findAll for getUser / getUserByLogin

● SearchService

Page 64: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● filter● take● flatMap

to asynchronously retrieve additional data needed for filter

Page 65: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

filter

Page 66: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Count4

Page 67: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

RankingService○ use from for rankByHashrate / rankByCoins○ complete migration for other methods

Page 68: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● takeUntil● count● take

Page 69: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

takeUntil

Page 70: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

count

Page 71: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Time for a Break

:)

Page 72: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Side Effects5

Page 73: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

doOnXXX

● doOnNext● doOnError● doOnCompleted● doOnEach

Page 74: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

PoolService○ add a line of log each time a user connects

Page 75: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Combine6

Page 76: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Level: Simple

Concat

Page 77: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Level: Intermediate

Merge

Page 78: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Level: Advanced

Zip

Page 79: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

StatService.getAllStats● for each User

○ retrieve his hashrate○ retrieve how many coins he mined○ combine both and make a UserStat

Page 80: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Live & Let Die and Retryoo7

Page 81: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

The Problem

StatService.lastBlockFoundBy○ Has intermittent bug that causes it to crash with an

IndexOutOfBoundsException

○ We’d like to retry the call when this happens, to prevent the error.

Page 82: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

The Plan

Make the method Observable (generate in a defer, log in a doOnNext, pick the user via flatMap and elementAt…)

Migrate code as before, it still randomly fails

Make it automatically retry

Page 83: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

The Plan (how to test)

Edit the PoolController.lastBlock() method so it doesn’t catch and recover

Execute PoolControllerTest.testLastBlock() and verify it succeeds

Sometimes it should print several “ELECTED” messages, this is the retry in action

Page 84: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● defer● flatMap● elementAt● retry

Page 85: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

ElementAt

Page 86: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Retry

Page 87: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Chain8

Page 88: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

ExchangeRateService○ calls two external APIs: doge-to-dollar rate and

currency-to-currency exchange rate○ two chained REST calls○ combination of the two gives doge-to-anyCurrency

Page 89: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● Observable.create○ wrap the REST call on each subscription○ catch RestClientException and make them into

DogePoolException (especially for timeouts)

Page 90: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Useful Operators

● zipWith○ similar to zip but called from stream A instead of

statically○ combine both rates to get the final one

Page 91: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Oh Hey!

! WARNING - Incoming Product Owner !

Page 92: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

"this free exchange rate API crashes too often,make it so we switch to an alternative paid APi when it’s the case"

- the Product Owner

Page 93: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

"this free exchange rate API crashes too often,make it so we switch to an alternative paid APi when it’s the case"

- the Product Owner!

Page 94: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

"oh yeah and if you could go on and

track costs of these callsit would be great"

- the Product Owner, pouring himself a coffee

Much SurpriseSuch Requirements

wow

Page 95: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

The Plan

● AdminService○ add method+variable to track cost for this month

● ExchangeRateService○ rate retrieval method similar to current one○ use endpoint from exchange.nonfree.api.baseUrl

● switch thanks to OnErrorResumeNext

● use side effects○ log when we switch & track the cost

Page 96: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

OnErrorResumeNext

Page 97: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

OnErrorReturn

Page 98: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Clean-up Controllers9

Page 99: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Asynchronous Response

● prepare a DeferredResult<T>○ that will be returned without blocking

● subscribe on stream○ onNext: inject T via setResult○ onError: create a DogePoolException and inject it via

setErrorResult

Page 100: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

This could be Generalized

● using ReturnValueHandler and a simple adapter of Observable to DeferredResult

● each time an Observable is returned, it’ll be converted into this adapter○ WebAsyncUtils.getAsyncManager(...).

startDeferredResultProcessing(...)

Page 101: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Testing

● using mockMvc’s andReturn() to get a MvcResult ○ assert status().isOk() and request().asyncStarted()

● trigger the async processing○ mockMvc.perform(asyncDispatch(mvcResult))

● from this point assert as before

Page 102: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Migrate Services

● AdminController (simple)

● IndexController (trickier)○ use zip, flatMap, single… to detect bad users

● UserProfileController (idem)

Page 103: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Q&A

Page 104: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

TakeAway

Page 105: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Nonblocking code

Page 106: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

without Callbacks

Page 107: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

with a minimum of visual cluter

Page 108: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

readable and understandable

Page 109: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Hopeyou loved it!

Page 110: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application
Page 111: Practical RxJava - Jfokus · Practical RxJava @Couchbase @InfoQFR @bbl_fr @SimonBasle. the Plan & Goals. RxJava 101. migrate a Legacy application RxJava 101. migrate a Legacy application

Merci!