In this particular article we will try to answer such questions like:

What is the reactive programming? What is the Functional Reactive Programming? What benefits we can get out of using Rx in our applications and where you can start from to cut Rx in to your application.

What is Reactive Programming?

Probably in each article about Reactive Programming you may find reference and link to Reactive Manifesto. In this document you can get the main statements about Reactive Application benefits, but it does not give you any idea about how to achieve them, though.

In fact, Reactive Manifesto is just a list of the main pillars that your reactive application must be concerned about. Specifically such as: Responsive, Resilient, Elastic and Message Driven.

If we try to express the whole idea in one sentence, we can get something like this:

Reactive programming gives us ability to create highly stable and responsive applications that can be easily modified or extended according to message driven approach. To put these benefits into your application you can use Reactive Programming. So what is it, Reactive Programming?

Reactive programming is an approach that is based on principles of asynchronous data streams and immutable data. It’s built on such basic concepts as Observables, Observers and Schedulers. First two are some sort of realization of time-honored Observer pattern. And Schedulers help with asynchronous programming and thread management.

For example, if you subscribe to some youtube channel you will receive notifications about new videos or streams, and check it if you wish. Same is for your project, you can subscribe to some event and react on it in accordance with your app logic. Schedulers come to stage if, for example, you emit event in background thread and need to react on it in main thread.

Functional Reactive Programming

Almost all modern Rx libraries use basic principles of Functional programming. As you may know, in functional programming you manipulate functions, and same way you manipulate other data types like integers or strings, and all these values are immutable.

In Functional Programming you always make deal with immutable piece of data, this fact allows you not to care about concurrency and current data states, which gives you greater advantages of using asynchronous multiple threads architecture. Also, as functional programming gives you predictable behavior it’s much easier to cover all your logic with Unit Tests. This, potentially, can give you more stable product.

FRP uses the best out of Reactive and Functional programming. In traditional programming we also use event streams to receive user activity, like button press, changing device orientation, and others. In FRP variables, user input, responses from server, parameters of models, and models itself can be represented as a stream. It rises up the level of abstraction, so you are able to manipulate the streams instead of objects or functions.

Main substance of FRP is Observable, that has wide range of operators using which you actually will implement your application business logic. The main categories of such operators are: Transform Observables, Filter Observables, Combine Observables, and others. The full list and descriptions to them you can find here.

It may seem pretty difficult for understanding. Fortunately for better understanding of Reactive Programming logic we can use Marble Diagrams like this:

You can find such diagrams for different operators that illustrate their work here.

Functional Reactive Programming using Swift

Okay, so how to achieve these results for your application? To apply Rx to you particular project you can use one of the Rx libraries, list of which you can find here.

For example, let’s use RxSwift and try some basic operators.

Let’s start with the “filter” operator.

“The Filter operator filters an Observable by only allowing items through that pass a test that you specify in the form of a predicate function”.

let disposeBag = DisposeBag() // Create an observable of integers Observable.of(1, 2, 3, 4, 5, 6) // Apply filter operator .filter { integer in integer % 2 == 0 } // Subscribe only on even numbers .subscribe(onNext: { print($0) }) .disposed(by: disposeBag) CONSOLE OUTPUT: 2 4 6 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 let disposeBag = DisposeBag ( ) // Create an observable of integers Observable . of ( 1 , 2 , 3 , 4 , 5 , 6 ) // Apply filter operator . filter { integer in integer % 2 == 0 } // Subscribe only on even numbers . subscribe ( onNext : { print ( $ 0 ) } ) . disposed ( by : disposeBag ) CONSOLE OUTPUT : 2 4 6

As you can see in this example we created an Observable of predefined integers. Then we filtered the even values and subscribed to this Observable. Combining operators together is quite flexible and lets you compose really powerful expressions.

As another example, check this piece of code with a “flatMap” operator.

“The FlatMap operator transforms an Observable by applying a function that you specify to each item emitted by the source Observable, where that function returns an Observable that itself emits items. FlatMap then merges the emissions of these resulting Observables, emitting these merged results as its own sequence.”

struct Video { var subscribers: Variable<Int> } let disposeBag = DisposeBag() let cat = Video(subscribers: Variable(30)) let bird = Video(subscribers: Variable(43)) let dog = Video(subscribers: Variable(20)) let channel = PublishSubject<Video>() channel.asObservable() .filter { video in video.subscribers.value > 20 } .flatMap { $0.subscribers.asObservable() } .subscribe(onNext: { print($0) }) .disposed(by: disposeBag) channel.onNext(cat) channel.onNext(bird) channel.onNext(dog) cat.subscribers.value = 40 dog.subscribers.value = 70 bird.subscribers.value = 123 dog.subscribers.asObservable() .subscribe(onNext: { print($0) }) .disposed(by: disposeBag) dog.subscribers.value = 80 CONSOLE OUTPUT: 30 43 40 123 70 80 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 struct Video { var subscribers : Variable < Int > } let disposeBag = DisposeBag ( ) let cat = Video ( subscribers : Variable ( 30 ) ) let bird = Video ( subscribers : Variable ( 43 ) ) let dog = Video ( subscribers : Variable ( 20 ) ) let channel = PublishSubject < Video > ( ) channel . asObservable ( ) . filter { video in video . subscribers . value > 20 } . flatMap { $ 0.subscribers.asObservable ( ) } . subscribe ( onNext : { print ( $ 0 ) } ) . disposed ( by : disposeBag ) channel . onNext ( cat ) channel . onNext ( bird ) channel . onNext ( dog ) cat . subscribers . value = 40 dog . subscribers . value = 70 bird . subscribers . value = 123 dog . subscribers . asObservable ( ) . subscribe ( onNext : { print ( $ 0 ) } ) . disposed ( by : disposeBag ) dog . subscribers . value = 80 CONSOLE OUTPUT : 30 43 40 123 70 80

In this example, first of all, we created the struct “Video” with only one observable parameter “subscribers”. One of the ways to revive events from those observables is to subscribe to each of them, but thanks to “flatMap” we can achieve similar result in more elegant way. So basically we create new PublicSubject “channel” and use “flatMap” operator to get stream with all these observables. Then we subscribe to them to print the values on the screen.

As I’ve mentioned before, we can combine operators to get more complex functionality. In this case we use “filter” before “flatMap” to observe only videos with subscriber’s.value higher than twenty. As a result, modification of “dog” video does not trigger print out event until we subscribe to it directly.

For better understanding check this diagram of “flatMap” operator:

What next?

At this point, you can start to bring Rx to your application. Just pick one of the libraries for your platform from here. All of them have quite good documentation but as a beginner you might need some additional information to start use Rx in best practice. Luckily nowadays on market we have a lot of good books for different platforms which describe specific cases of usage of Rx libraries. For example, if you work with swift like I do, I recommend to look in this RxSwift book created by the raywenderlich.com Tutorial Team.