All Projects → anitaa1990 → RxNetworkEvent-Example

anitaa1990 / RxNetworkEvent-Example

Licence: other
This is a sample app to demonstrate error handling using Retrofit2 and RxJava2

Programming Languages

java
68154 projects - #9 most used programming language

RxNetworkEvent-Example

The Kotlin version of the project can be found under migrate_to_kotlin branch.

I recently had a requirement to handle error scenarios in apis. I have rest apis in the app and needed to handle no internet/ no service available / unauthorised errors in a generic way. i.e. I wanted to display an error dialog every time any api in the app throws a 503 or 401 error response.

This is the scenario I had to implement.

There are 5 steps to this implementation.

1. Create NetworkState enum
We are going to create an enum class that holds the different api error states that can happen. (In my use case, I only needed to handle these 3 error states but you could add states more if you like).

2. Create NetworkEvent class
We create a new class NetworkEvent (ignore the name please :) ). This is our RxEventBus class. We are going to:

  • Make this class a Singleton. You can checkout more about how to implement a Singleton class from here.
  • Create a PublishSubject instance in the class: PublishSubject can be used to publish events to all registered subscribers in the app. This is a single instance since I have only one event I need to publish. If we have multiple events, we can create a map to keep track of the different types of subjects.
  • Create a CompositeDisposable map in the class: We use CompositeDisposable to maintain the list of subscriptions in a pool. And also to so that we can dispose them all at once. (For example, when an activity is destroyed, it no longer needs to subscribe to the rest events right? So we need to remove the subscription in order to avoid memory leaks). The reason we have a map of CompositeDisposable is so that we can keep track of all the subscriptions for a given object (typically an Activity or Fragment). So the key of the map will be the Activity or fragment instance and the value of the map will a new CompositeDisposable instance.
  • Create 3 methods in the class:
    • publish(NetworkState networkState) — Method to publish the NetworkState event to all the subscribers subscribed to the changes in this event.
    • register(Object lifecycle, Consumer<NetworkState> action) — Method to subscribe to the specified subject and listen for updates on that subject. Pass in an object (in this case the activity or fragment instance) to associate the registration, so that we can unsubscribe later.
    • unregister(Object lifecycle) — Method to unregister this particular object from the bus, removing all subscriptions. This should be called in order to avoid memory leaks.

3. Create an interceptor class — NetworkInterceptor
This class will check the error response from all the api responses. If the response code is 401 or 503, then we are publishing the network event to the UI. We use the ConnectivityStatus class to check if internet is available in the device. Note that you need to have ACCESS_NETWORK_STATE permission declared in the app is order to get updates about the network status in a device.

4. Add the interceptor to the Retrofit service

5. Register & unregister a subscriber - BaseActivity
So in my use case, I had only one subscriber. I had created a BaseActivity class that all activities inherit, which means, regardless of which screen the user is at, if an api fails, the subscriber will be notified of it and we can display our error message.

You can simply use this one NetworkEvent class to communicate between different parts of your app. This solution might not be perfect but I felt it was a good compromise between complexity and ease of use. You can use this solution as is if you want, or tweak it to fit your needs.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].