com.yossisegev.apiwithrxjavademo.api.ApiObservable.java Source code

Java tutorial

Introduction

Here is the source code for com.yossisegev.apiwithrxjavademo.api.ApiObservable.java

Source

/*
 *  Copyright 2015 Yossi Segev.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.yossisegev.apiwithrxjavademo.api;

import android.util.Log;

import com.squareup.okhttp.Call;
import com.squareup.okhttp.OkHttpClient;
import com.squareup.okhttp.Request;
import com.squareup.okhttp.Response;

import rx.Observable;
import rx.Subscriber;
import rx.android.schedulers.AndroidSchedulers;
import rx.functions.Action0;
import rx.schedulers.Schedulers;

public class ApiObservable<T extends ApiResponse> implements Observable.OnSubscribe<T> {

    private static final String TAG = "ApiObservable";
    private static OkHttpClient mOkHttpClient;
    private final Class<T> mApiResponse;
    private final ApiRequest mApiRequest;
    private Call mCall;
    private Response mResponse;
    private Observable<T> mObservable;

    public static <E extends ApiResponse> Observable<E> create(final ApiRequest apiRequest, Class<E> apiResponse) {

        ApiObservable<E> apiObservable = new ApiObservable<>(apiRequest, apiResponse);
        return apiObservable.getObservable();
    }

    private ApiObservable(final ApiRequest apiRequest, Class<T> apiResponse) {

        if (mOkHttpClient == null) {
            mOkHttpClient = new OkHttpClient();
        }

        mApiRequest = apiRequest;
        mApiResponse = apiResponse;
        mObservable = buildObservable();
    }

    private Observable<T> buildObservable() {

        return Observable.create(this).doOnUnsubscribe(unsubscribeAction).subscribeOn(Schedulers.io())
                .unsubscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread());
    }

    @Override
    public void call(Subscriber<? super T> subscriber) {

        try {

            // Building
            Request request = mApiRequest.buildRequest();

            // Sending
            Log.i(TAG, "Executing: " + mApiRequest);
            mCall = mOkHttpClient.newCall(request);
            mResponse = mCall.execute();

            // Parsing
            if (mResponse.isSuccessful()) {

                String responseStr = mResponse.body().string();
                T responseObj = mApiResponse.newInstance();
                boolean parsedSuccessfully = responseObj.parseResponse(responseStr);

                if (parsedSuccessfully) {
                    subscriber.onNext(responseObj);
                    subscriber.onCompleted();

                } else {
                    subscriber.onError(new Exception("Parsing failed: " + responseStr));
                }

            } else {
                subscriber.onError(new Exception(mResponse.message()));
            }

        } catch (Exception e) {
            // Catch everything
            subscriber.onError(e);
        }
    }

    // Called when unsubscribing.
    Action0 unsubscribeAction = new Action0() {
        @Override
        public void call() {

            // Check if we have a running Call to cancel
            if (mCall != null && mResponse == null) {
                Log.i(TAG, "Cancelling: " + mApiRequest);
                mCall.cancel();
            }
        }
    };

    private Observable<T> getObservable() {
        return mObservable;
    }
}