美文网首页Android
利用Retrofit+RxJava实现网络请求的异常处理

利用Retrofit+RxJava实现网络请求的异常处理

作者: 耀东wang | 来源:发表于2018-08-02 16:01 被阅读1060次

    通常情况下我们在与服务器进行通信的时候,不一定就不会出错,有时会出现其他的错误,这个时候我们只要和服务器约定好各种异常,在返回结果处进行判断,到底是执行错误,还是返回正常数据。具体的思路大致就是这样。这里我们定义ExceptionHandle,这里我参考网上的东西,然后稍微做了一些改动。
    ExceptionHandle

    public class ExceptionHandle {
    
        private static final int UNAUTHORIZED = 401;
        private static final int FORBIDDEN = 403;
        private static final int NOT_FOUND = 404;
        private static final int REQUEST_TIMEOUT = 408;
        private static final int INTERNAL_SERVER_ERROR = 500;
        private static final int BAD_GATEWAY = 502;
        private static final int SERVICE_UNAVAILABLE = 503;
        private static final int GATEWAY_TIMEOUT = 504;
    
        public static ResponseException handleException(Throwable e){
            //转换成ResponseException,根据状态码判定错误信息
            ResponseException ex;
            if(e instanceof HttpException){
                HttpException httpException=(HttpException)e;
                /**
                 * 传入状态码,根据状态码判定错误信息
                 */
                ex=new ResponseException(e,ERROR.HTTP_ERROR);
                switch (httpException.code()){
                    case UNAUTHORIZED:
                        ex.message="未验证";
                        break;
                    case FORBIDDEN:
                        ex.message="服务禁止访问";
                        break;
                    case NOT_FOUND:
                        ex.message="服务不存在";
                        break;
                    case REQUEST_TIMEOUT:
                        ex.message="请求超时";
                        break;
                    case GATEWAY_TIMEOUT:
                        ex.message="网关超时";
                        break;
                    case INTERNAL_SERVER_ERROR:
                        ex.message="服务器内部错误";
                        break;
                    case BAD_GATEWAY:
    
                        break;
                    case SERVICE_UNAVAILABLE:
                        break;
                    default:
                        ex.message = "网络错误";
                        break;
                }
                return ex;
            }else if(e instanceof JsonParseException
                    || e instanceof JSONException
                    || e instanceof ParseException){
                ex=new ResponseException(e,ERROR.PARSE_ERROR);
                ex.message="解析错误";
                return ex;
            }else if(e instanceof ConnectException){
                ex=new ResponseException(e,ERROR.NETWORD_ERROR);
                ex.message="连接失败";
                return ex;
            }else if(e instanceof javax.net.ssl.SSLHandshakeException){
                ex=new ResponseException(e,ERROR.SSL_ERROR);
                ex.message="证书验证失败";
                return ex;
            }else {
                ex=new ResponseException(e,ERROR.UNKNOWN);
                ex.message="未知错误";
                return ex;
            }
        }
        /**
         * 约定异常
         */
      public static   class ERROR{
            /**
             * 自定义异常
             */
            private static final int UNAUTHORIZED = 401;//请求用户进行身份验证
            private static final int UNREQUEST=403;//服务器理解请求客户端的请求,但是拒绝执行此请求
            private static final int UNFINDSOURCE=404;//服务器无法根据客户端的请求找到资源
            private static final int SEVERERROR=500;//服务器内部错误,无法完成请求。
            /**
             * 协议出错
             */
            public static final int HTTP_ERROR = 1003;
            /**
             * 未知错误
             */
            public static final int UNKNOWN = 1000;
            /**
             * 解析错误
             */
            public static final int PARSE_ERROR = 1001;
            /**
             * 网络错误
             */
            public static final int NETWORD_ERROR = 1002;
            /**
             * 证书出错
             */
            public static final int SSL_ERROR = 1005;
        }
        /**
         * 自定义Throwable
         */
        public static class ResponseThrowable extends Exception{
            public int code;
            public String message;
            public ResponseThrowable(Throwable throwable,int code){
                super(throwable);
                this.code=code;
            }
        }
        /**
         * 服务器异常
         */
        public class ServerException extends RuntimeException{
            public int code;
            public String message;
        }
    
        /**
         * 统一异常类,便于处理
         */
        public static class ResponseException extends Exception{
            public int code;
            public String message;
            public ResponseException (Throwable throwable,int code){
                super(throwable);
                this.code=code;
            }
        }
    }
    

    然后自己定义了一个Observer

    public abstract class BaseObserver<T> implements Observer<T> {
        private Context context;
    
        public BaseObserver(Context context){
            this.context=context;
        }
    
        @Override
        public void onSubscribe(Disposable d) {
    
        }
        @Override
        public void onNext(T t) {
    
        }
        @Override
        public void onError(Throwable e) {
            if(e instanceof ExceptionHandle.ResponseException){
                onError((ExceptionHandle.ResponseException)e);
            }else{
                onError(new ExceptionHandle.ResponseException(e,ExceptionHandle.ERROR.UNKNOWN));
            }
        }
        @Override
        public void onComplete() {
    
        }
        public abstract void onError(ExceptionHandle.ResponseException exception);
    }
    

    这里发生错误时,Observerble会先调用onError(Throwable e),按照我的写法呢,会继续调用自定义onError。

    那么什么时候我们对服务器的返回结果进行判断,什么时候该发出异常了,请继续往下看:

    这里我们打算用到ObservableTransformer,Transformer其实就是就是对Observable进行一定的变换。
    先看代码:

        public static class HandleFuc<T> implements Function<UserGuideSoftConfigRForm<UserGuideSoftConfigPageInfo<List<UserguideSoftConfig>>>, T> {
            @Override
            public T apply(UserGuideSoftConfigRForm<UserGuideSoftConfigPageInfo<List<UserguideSoftConfig>>> Response) {
                if (!Response.getCode().equals("200")){
                    Throwable e=new Throwable("约定错误");
                    /**
                     * 可以根据不同的状态嘛返回不同的提示信息
                     * 与服务器约定返回异常信息
                     */
                    ExceptionHandle.ResponseException responseException = new ExceptionHandle.ResponseException(e, ExceptionHandle.ERROR.HTTP_ERROR);
                    return (T) Observable.error(responseException);//发出错误异常
                }
                return (T) Observable.just(Response);//发出服务器数据,返回Observable<Response>
            }
        }
    
        //处理错误的变换
        public static class ErrorTransformer<T> implements ObservableTransformer {
            @Override
            public Observable<T> apply(Observable upstream) {
                return (Observable<T>) upstream.flatMap(new HandleFuc<T>());//flatMap会重新创建一个Observable,当它处理完事件后会汇入原先的Observable对象。
            }
        }
    

    说明:我们的HandleFuc其实就是对服务器返回来的结果进行判断,逻辑很简单了,错误就抛出异常直接执行error方法。如果没有错误,就发送正常数据。这里值的说明一点的是,flatMap会重新创建一个Observable,当它处理完事件后会重新汇入初始的Observerble并开始发送事件。

    使用起来其实就很简单了:

    @Provides
        ErrorTransformer provideErrorTransformer(){
            return new ErrorTransformer();
        }
    
     public Observable<UserGuideSoftConfigRForm<UserGuideSoftConfigPageInfo<List<UserguideSoftConfig>>>> getApplication(PageParmForm pageParmForm){
            return retrofit.create(Service.class)
                    .getApplicationList(pageParmForm)
                    .compose(errorTransformer)
                    .subscribeOn(Schedulers.io())
                    .observeOn(AndroidSchedulers.mainThread());
        }
    

    直接用compose方法包裹起来即可。

    最后看看Activity:

    new NetRepository().getApplication(new PageParmForm(Constant.orderStr,Constant.pageNum,Constant.pageSize))
            .subscribe(new BaseObserver<UserGuideSoftConfigRForm<UserGuideSoftConfigPageInfo<List<UserguideSoftConfig>>>>(NetWorkActivity.this) {
                @Override
                public void onError(ExceptionHandle.ResponseException exception) {
                    myToast.showToast(NetWorkActivity.this,exception.getMessage());
                    Log.d("carhandbook",exception.getMessage());
                }
    
                @Override
                public void onNext(UserGuideSoftConfigRForm<UserGuideSoftConfigPageInfo<List<UserguideSoftConfig>>> Response) {
                    data=Response.getData().getList();
                    code=Response.getCode();
                    myToast.showToast(NetWorkActivity.this,code);
                    generateAdapter.setData(data);
                    generateAdapter.notifyDataSetChanged();
                }
            });
    

    好了对网络请求的异常处理整个思路大致就是这样了。

    相关文章

      网友评论

        本文标题:利用Retrofit+RxJava实现网络请求的异常处理

        本文链接:https://www.haomeiwen.com/subject/jyfsvftx.html