Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Javantura v3 - Going Reactive with RxJava – Hrvoje Crnjak

1,334 views

Published on

Javantura v3 - Going Reactive with RxJava – Hrvoje Crnjak

Published in: Technology
  • Be the first to comment

  • Be the first to like this

Javantura v3 - Going Reactive with RxJava – Hrvoje Crnjak

  1. 1. Going Reactive with RxJava JAVANTURA Zagreb – February 2016 Hrvoje Crnjak Java Developer @ Five @HrvojeCrnjak FIVE
  2. 2. Going Reactive with RxJava
  3. 3. So what does it mean for the App to be Reactive? His Majesty Reactive Manifesto
  4. 4. ReactiveApp should be … Message-Driven • Components communicate via asynchronous messages (errors are messages also) Resilient • System stays responsive in the face of failure Elastic (Scalable) • System stays responsive under varying workload Responsive • System responds in timely manner if at all possible
  5. 5. Or if we put it in a diagram … Resilient Message-Driven Scalable Responsive
  6. 6. OOP, State of the Union Resilient Message-Driven Scalable Responsive We’ll pack Events into Messages TheGood TheBad TheUgly State and Behavior are Joined State is Mutated Error Handling up to the Client
  7. 7. So how does RxJava fit into all of this?
  8. 8. Event-Driven → Message-Driven Everything is a message • Including errors Everyone (each component) can be Producer and Consumer of messages Producer Consumer Stream of Messages UI Component Remote Service Scheduled Job Whoever’s Subscribed Events Computation Result Query Result
  9. 9. Making Streams of Messages with RxJava Observable – Representation of the Message Producer Observer – Representation of the Message Consumer • onNext • onCompleted • onError onNext onNext onNext onCompleted ObservableStream of Messages
  10. 10. Making Streams of Messages with RxJava Observable – Representation of the Message Producer Observer – Representation of the Message Consumer • onNext • onCompleted • onError onNext onNext onError ObservableStream of Messages
  11. 11. Making an Observable Predefined Observable templates • Observable.from • Observable.just • Factory Methods • Observable.interval , Observable.range , Observable.empty Observable<Long> intervalObservable = Observable.interval(500L, TimeUnit.MILLISECODS); Observable<Integer> rangeObservable = Observable.range(1, 10); Observable<Character> justObservable = Observable.just('R', 'x', 'J', 'a', 'v', 'a'); List<String> list = Arrays.asList("blue", "red", "green", "yellow", "orange"); Observable<String> listObservable = Observable.from(list)
  12. 12. Making an Observable The real Power lies in • Observable.create public static Observable<SomeDataType> getData(String someParameter) { return Observable.create(subscriber -> { try { SomeDataType result = SomeService.getData(someParameter); subscriber.onNext(result); subscriber.onCompleted(); } catch (Exception e) { subscriber.onError(e); } }); }
  13. 13. Consuming an Observable At it’s Core very simple • observableInstance.subscribe observableInstance.subscribe(new Observer<SomeDataType>() { @Override public void onNext(SomeDataType message) { // Do something on each Message received } @Override public void onError(Throwable error) { // Do something on Error } @Override public void onCompleted() { // Do something when Observable completes } });
  14. 14. Consuming an Observable At it’s Core very simple • observableInstance.subscribe observableInstance.subscribe( (SomeDataType message) -> {/*onNext*/}, (Throwable error) -> {/*onError*/}, () -> {/*onCompleted*/});
  15. 15. OOP + RxJava, State of the Union Resilient Message-Driven Scalable Responsive Observer + Observable
  16. 16. Making the System Scalable How to approach the problem • Scale up – I don’t think so • Scale out – That’s more like it • A lot of Cores and Memory! Desired Characteristics of our System • Program logic should execute in Parallel • Data immutability is Allowed/Encouraged The answer • Functional programming
  17. 17. Making the System Scalable Why FP Approach • State HandledTransparently • Highly composable When we apply this to Rx world … • Data manipulation • Composable FP style Observable methods • State change • Each change of state will be a new message in the Stream
  18. 18. Composable methods with RxJava There are methods for • Content filtering • Time filtering • Data transformation • Stream composition observableInstance.filter(element -> element < 10) observableInstance.timeout(100, TimeUnit.MILLISECONDS) observableInstance.map(number -> number * number) Observable<String> mergedObservable = Observable .merge(firstObservable, secondObservable, thirdObservable);
  19. 19. Manipulating Streams with RxJava 1Observable.range(1,9) 2 3 4 5 6 7 8 9 5 6 7 8 9 .skipWhile(element -> element < 5) 5 6 7 .take(3) 18 .reduce((elem1, elem2) -> elem1 + elem2) .subscribe(result -> /*do something*/)
  20. 20. OOP + RxJava, State of the Union Observer + Observable Resilient Message-Driven Scalable Responsive Observable Methods (FP style) + Transparent State
  21. 21. WHEN the System Fails With classic OOP the Client has to • try/catch • Resource cleanup With RxJava the Client has to • onError • Error is a First-class Citizen onNext onNext onError ObservableStream of Messages
  22. 22. Recovering from Errors When the Error Occurs • Observable finishes • Observer’s recovery options • onErrorReturn , onErrorResumeNext, retry mainObservable.onErrorReturn(throwable -> { System.out.println("The original feed failed with" + throwable); return oneMoreMessage; }).subscribe(data -> {/* doSomething */}); mainObservable.onErrorResumeNext(throwable -> { System.out.println("The original feed failed with" + throwable); return backupObservable; }).subscribe(data -> {/* doSomething */});
  23. 23. OOP + RxJava, State of the Union Observer + Observable Error is a First- Class Citizen Resilient Message-Driven Scalable Responsive Observable Methods (FP style) + Transparent State
  24. 24. Let’s Get ResponsiVle Responsive • To Our Client • Already improved Scalability and Resilience • Asynchronous execution Responsible • To Our System (to our Resources)
  25. 25. Asynchronous Streams “Out of the Box” main Main thread Stack
  26. 26. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted)
  27. 27. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData()
  28. 28. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() remoteService.getData
  29. 29. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() subscriber.onNext(data)
  30. 30. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() subscriber.onNext(data) subscriber.onNext
  31. 31. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() subscriber.onNext(data) subscriber.onCompleted()
  32. 32. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() subscriber.onNext(data) subscriber.onCompleted() subscriber.onCompleted
  33. 33. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) observable.subscribe remoteService.getData() subscriber.onNext(data) subscriber.onCompleted()
  34. 34. Asynchronous Streams “Out of the Box” main Main thread Stack observable.subscribe (onNext, onCompleted) remoteService.getData() subscriber.onNext(data) subscriber.onCompleted()
  35. 35. Asynchronous Streams “Out of the Box” Main thread Stack empty observable.subscribe (onNext, onCompleted) remoteService.getData() subscriber.onNext(data) subscriber.onCompleted()
  36. 36. Asynchronous Streams Let’s get Asynchronous • Thread handling with Observable • subscribeOn(Scheduler) -Thread Observable will run on • observeOn(Scheduler) -Thread Observer will run on • Available Schedulers • immediate – use CallerThread • newThread – do work on newThread • trampoline – enqueue work on CallerThread • io – Thread pool used for IO tasks • computation – Thread pool used for Computation tasks
  37. 37. Asynchronous Streams Asynchronous in practice Main thread
  38. 38. Asynchronous Streams Asynchronous in practice Main thread observable .subscribeOn(Schedulers.io()) .observeOn(Schedulers.computation()) .subscribe(onNext, onCompleted)
  39. 39. Asynchronous Streams Asynchronous in practice Main thread observable .subscribeOn(Schedulers.io()) .observeOn(Schedulers.computation()) .subscribe(onNext, onCompleted) IOthread remoteService.getData() subscriber.onNext(data)
  40. 40. Asynchronous Streams Asynchronous in practice Main thread observable .subscribeOn(Schedulers.io()) .observeOn(Schedulers.computation()) .subscribe(onNext, onCompleted) IOthread remoteService.getData() subscriber.onNext(data) Computation thread
  41. 41. Asynchronous Streams Asynchronous in practice Main thread observable .subscribeOn(Schedulers.io()) .observeOn(Schedulers.computation()) .subscribe(onNext, onCompleted) IOthread remoteService.getData() subscriber.onNext(data) subscriber.onCompleted() Computation thread
  42. 42. Responsible Client Being Reactive isn’t just about doing something fast, it’s about not doing it at all. Or to be more precise, to do only what’s necessary.
  43. 43. Responsible Client Being Responsible • Observable works only when someone’s listening • subscribe triggers Observable Stream • Client (Consumer of Stream) tells us when he’s done listening • unsubscribe
  44. 44. Responsible Client Two flavors of Unsubscribing • Client (Consumer) is unsubscribed from “outside” Subscription subscription = observableInstance.subscribe( (Long message) -> {/*onNext*/}, (Throwable error) -> {/*onError*/}, () -> {/*onCompleted*/}); // Do some logic; subscription.unsubscribe();
  45. 45. Responsible Client Two flavors of Unsubscribing • Client (Consumer) is unsubscribed from “inside” observableInstance.subscribe(new Subscriber<Long>() { @Override public void onNext(Long message) { // Do something on each Message received unsubscribe(); } @Override public void onError(Throwable e) { // Do something on Error } @Override public void onCompleted() { // Do something when Observable completes } });
  46. 46. OOP + RxJava, State of the Union Observer + Observable Error is a First- Class Citizen Asynchronous + Resources on Demand Message-Driven Scalable Responsive Resilient Observable Methods (FP style) + Transparent State
  47. 47. Thanks for your time! Q & hopefully A

×