0

I am using an auto-generated AWS Android SDK to access my REST API. Example

Repos =  restClient.getRepos();

This call needs to be in an Async Task but I am converting it in an Observable by

final Observable reposRx = Observable.fromCallable(() -> restClient.getRepos());

The http client that uses the REST API uses a token for authentication, if I execute a method from the REST API and the token is expired it will throw an error so before i execute any REST call I need to check if the token has expired(This is done just checking in a sync method that checks a variable), if it's expired then I need to renew it by executing another async network call.

if(isTokenExpired()) { 
   refreshToken((new RefreshIdTokenCallback() {
       @Override 
       public void onSuccess(final String idToken) 
       {
         getRepos()
       }
       @Override
       public void onFailure(final Throwable error) 
       {
         //How to connect it with Rx
       }
      });
   }
   else
   {
     getRepos()
   }

So after the token is renewed I can now execute the original rest api call.

public void getRepos()
  {
   reposRx
   .subscribeOn(Schedulers.newThread())
   .observeOn(AndroidSchedulers.mainThread())    
   .subscribe(new Subscriber<Repos>() {
      @Override
      public void onCompleted() {
      }
      @Override
      public void onError(final Throwable e) {
      }
      @Override
      public void onNext(final Repos repos) {
            //update the list
      }
    });
}

Is there any magic way to convert everything to RxJava and also have a method that that I can reuse with all the REST API methods that checks the token expiration, if expired refreshes and calls the REST API. And also connects the onFailed ? (All with Rx)

Tassos Bassoukos
  • 16,017
  • 2
  • 36
  • 40
Kenenisa Bekele
  • 835
  • 13
  • 34
  • Use retrofit for that, It will return your response in Observable, and it will allow to intercept request in order to refresh session token: http://stackoverflow.com/questions/25546934/retrofit-rxjava-and-session-based-services/25551689#25551689 – Than Aug 29 '16 at 18:42
  • I know that with retrofit is easier but I cannot use retrofit on this one, it's using the auto generated AWS SDK for Android – Kenenisa Bekele Aug 29 '16 at 19:04

1 Answers1

0

Having no idea of the API, let me try a first stab at it:

Observable<String> refresh = Observable.defer(() ->    
  Observable<String>.create(subscriber -> {
    refreshToken(new RefreshIdTokenCallback() {
      @Override 
      public void onSuccess(final String idToken) 
      {
        subscriber.onNext(idToken);
        subscriber.onComplete();
      }
      @Override
      public void onFailure(final Throwable error) 
      {
        subscriber.onError(error);
      }
    })
  })
  .subscribeOn(Schedulers.newThread())
);

Observable<?> checkExpiration = 
    Observable
    .defer(() -> Observable.just(isTokenExpired()))
    .flatMap(expired -> expired ? refresh : just(""));

Now, you can hook up to checkExpiration however you want; it emits a single dummy item, and you can use that to map or flatMap any way you like.

Tassos Bassoukos
  • 16,017
  • 2
  • 36
  • 40