package com.gertherb.authentication;
import android.accounts.AccountManager;
import android.os.Bundle;
import com.gertherb.R;
import com.novoda.notils.logger.simple.Log;
import com.novoda.rx.core.ObservableVault;
import com.novoda.rx.core.ObserverFactory;
import com.novoda.rx.core.ResumableReference;
import com.novoda.rx.core.ResumableSubscriber;
import com.novoda.rx.core.observer.ResumableObserver;
import com.novoda.rx.exception.CancelledException;
import rx.Observable;
import rx.Observer;
import rx.android.schedulers.AndroidSchedulers;
import rx.functions.Func1;
import rx.schedulers.Schedulers;
public abstract class ReactiveAuthenticatorActivity<T> extends BetterAuthenticatorActivity implements ObserverFactory, ResumableReference {
private ResumableSubscriber resumableSubscriber;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
resumableSubscriber = new ResumableSubscriber(this, this, getObservebleVault());
}
@Override
protected void onStart() {
super.onStart();
initLoginProcess();
}
@Override
protected void onResume() {
super.onResume();
resumableSubscriber.resume();
}
@Override
protected void onPause() {
super.onPause();
resumableSubscriber.pause();
}
protected abstract ObservableVault getObservebleVault();
protected abstract Observable<T> getCredentialsObservable();
protected abstract Observable<Token> getTokenObservable(T credentials);
private void initLoginProcess() {
getCredentialsObservable().subscribe(new Observer<T>() {
@Override
public void onCompleted() {
}
@Override
public void onError(Throwable e) {
Log.e("Error retrieving user credentials", e);
}
@Override
public void onNext(T credentials) {
resumableSubscriber.subscribe(getTokenObservable(credentials)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread()), new TokenObserver());
}
});
}
protected void handleError(Throwable throwable) {
setErrorResultAuthenticator(AccountManager.ERROR_CODE_REMOTE_EXCEPTION, throwable);
}
@Override
public ResumableObserver createObserver(int code) {
switch (code) {
case TokenObserver.ID:
return new TokenObserver();
default:
throw new IllegalArgumentException("No case defined for id " + code);
}
}
private Func1<T, Observable<? extends Token>> login() {
return new Func1<T, Observable<? extends Token>>() {
@Override
public Observable<? extends Token> call(T credentials) {
return getTokenObservable(credentials);
}
};
}
private class TokenObserver implements ResumableObserver<Token> {
private static final int ID = R.id.token_observer;
@Override
public int getId() {
return 0;
}
@Override
public void onCompleted() {
}
@Override
public void onError(Throwable throwable) {
if (throwable instanceof CancelledException) {
setCancelResultAuthenticator(throwable);
return;
}
handleError(throwable);
}
@Override
public void onNext(Token token) {
setSuccessResponse(token);
}
}
}