Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android retrofit handle onFailure() response

I have been developing android app, wheream using Retrofit.

In that how to handle onFailure(Throwable t) callback for NoInternetConnection and OtherError

I have check some questions on stackoverflow, but it didn't helped, because am using retrofit 2

compile 'com.squareup.retrofit2:retrofit:2.1.0'

Callback Code

    public class AvsCallBack<T> implements Callback<T> {
        private static final String TAG = "AvsCallBack";
        private AvsCallbackInterface<T> avsInterface;
        private Activity activity;
        private boolean validateError = true;

        public AvsCallBack(Activity activity, AvsCallbackInterface<T> avsInterface) {
            this.activity = activity;
            this.avsInterface = avsInterface;
        }

        public AvsCallBack(Activity activity, AvsCallbackInterface<T> avsInterface, boolean validateError) {
            this.activity = activity;
            this.avsInterface = avsInterface;
            this.validateError = validateError;
        }

        @Override
        public void onResponse(Call<T> call, Response<T> response) {
            if (response.isSuccessful()) {
                if (BuildConfig.DEBUG) Log.d(TAG, new Gson().toJson(response.body()));
                avsInterface.onSuccess(call, response.body());
            } else {
                onFailure(call, null);
            }
        }

        @Override
        public void onFailure(Call<T> call, Throwable t) {
            if (validateError) {
                if (BuildConfig.DEBUG)
                    Log.d(TAG, "Retrofit Exception -> " + ((t != null && t.getMessage() != null) ? t.getMessage() : "---"));
                if (t != null && (t instanceof IOException || t instanceof SocketTimeoutException || t instanceof ConnectException)) {
                    if (t instanceof SocketTimeoutException || t instanceof TimeoutException) {
                        ((BaseActivity) activity).showToast("Oops something went wrong");
                        //avsInterface.onError(call, new AvsException("Oops something went wrong, please try again later..."));
                    } else {
                        ((BaseActivity) activity).showToast("Please check your internet connection...");
                        //avsInterface.onError(call, new AvsException("Please check your internet connection..."));
                    }
                } else {
                   ((BaseActivity) activity).showToast("Oops something went wrong");
                }
                if (BuildConfig.DEBUG)
                    Log.d(TAG, "Avs Exception -> " + ((t != null && t.getMessage() != null) ? t.getMessage() : "---"));
            }
            avsInterface.onError(call, t);
        }
    }

MyInterface

public interface AvsCallbackInterface<T> {

    void onSuccess(Call<T> call, T t);

    void onError(Call<T> call, Throwable throwable);
}
like image 672
Arun Shankar Avatar asked Mar 27 '17 08:03

Arun Shankar


People also ask

What is onFailure?

onFailure(Call<T> call, Throwable t) Invoked when a network exception occurred talking to the server or when an unexpected exception occurred creating the request or processing the response. void. onResponse(Call<T> call, Response<T> response) Invoked for a received HTTP response.

What is retrofit2?

What is Retrofit. Retrofit is a REST Client for Java and Android allowing to retrieve and upload JSON (or other structured data) via a REST based You can configure which converters are used for the data serialization, example GSON for JSON.


2 Answers

Quote from here:

When Throwable is passed to the failure, the callback is an IOException, this means that it was a network problem (socket timeout, unknown host, etc.). Any other exception means something broke either in serializing/deserializing the data or it's a configuration problem.

You can do t instanceof IOException to determine network problem and react appropriately.

A 401 (or any non-2xx response code) will actually go to the response callback, because it was a successful response even though it may not have been a successful operation on the server. You can check this in onResponse by calling response.isSuccess().

like image 167
Rissmon Suresh Avatar answered Oct 26 '22 14:10

Rissmon Suresh


What I do is use a interceptor for request which checks for internet connectivity and responds accordingly. In my case I use MPV so it automatically call BasePresenter method.

Interceptor:

class NetworkStatusInterceptor implements Interceptor {

        @Override
        public Response intercept(Chain chain) throws IOException {
            if (!Util.isInternet(mContext)) {
              return new Response.Builder()
                      .code(1007)
                      .request(chain.request())
                      .protocol(Protocol.HTTP_2)
                      .body(ResponseBody.create(MediaType.parse("{}"),"{}"))
                      .message(mContext.getString(R.string.warning_no_internet))
                      .build();
            }
            return chain.proceed(chain.request());
        }
    }

Attach interceptor to OkHTTPClient:

 builder.addInterceptor(new NetworkStatusInterceptor());

You can handle this in your onResponse:

public void onResponse(final Call<T> call, final Response<T> response) {
        if (response.code() == 1007) {
          // handle no internet error
       }
    }
like image 24
Pwn Avatar answered Oct 26 '22 14:10

Pwn