RxJava 2とRetrofit 2のパッケージと使用

9067 ワード

RxJava 2とRetrofit 2によるカプセル化により,ネットワークリクエストがより容易になる.
demoダウンロードアドレス:https://github.com/sundevin/rxjava2_retrofit2
現在の実装:
1、統一スタイルのインターフェース
2、統一されていないスタイルのインターフェース
3、メモリ漏れの問題
4,要求中ProgressDialog
5,カスタム証明書のHttpsのパッケージ
6,okHttpによるダウンロード時の進捗コールバックのパッケージ
後で進捗コールバック付きアップロード機能を実現します.
Restfulスタイルのインタフェースに対して直接汎用型を指定することができる.内部にStringConverterFactoryが追加され、Restfulスタイルではないインタフェース(サードパーティインタフェースのデータなど)がStringに直接取得され、自分でデータ解析を行うことができます.ネットワークリクエスト中に現在のActivityにバインドすることができ、Activityがオフになったときにリクエストをアクティブに停止し、メモリの漏洩を回避します.ProgressDialogを表示するかどうかを決定することもできます.データ要求の前後にrequestとresponse情報を印刷し、インタフェースのデバッグをより直感的に行うことができる.httpはパッケージ化されており、自己署名証明書を指定するだけでよい.okHttpリクエストを使用する場合は、進捗コールバックとダウンロードのキャンセルをサポートします.
初期構成
1、プロジェクト依存
    compile 'io.reactivex.rxjava2:rxjava:2.0.7'
    compile 'io.reactivex.rxjava2:rxandroid:2.0.1'

    compile 'com.squareup.retrofit2:retrofit:2.2.0'
    compile 'com.squareup.retrofit2:converter-gson:2.2.0'
    compile 'com.squareup.retrofit2:adapter-rxjava2:2.2.0'

    compile 'com.trello.rxlifecycle2:rxlifecycle:2.0.1'
    // If you want to bind to Android-specific lifecycles
    compile 'com.trello.rxlifecycle2:rxlifecycle-android:2.0.1'
    // If you want pre-written Activities and Fragments you can subclass as providers
    compile 'com.trello.rxlifecycle2:rxlifecycle-components:2.0.1'
実行時に依存エラーが発生する可能性があります.androidTestCompileでは次のように構成されています.
    androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
        exclude group: 'com.android.support', module: 'support-annotations'
        exclude group: 'com.google.code.findbugs', module: 'jsr305'
    })
2,OkHttp構成
        CustomHttpsTrust customHttpsTrust = new CustomHttpsTrust(CertificateManager.trustedCertificatesInputStream());

        okHttpClient = new OkHttpClient.Builder()
                .connectTimeout(CONNECT_TIMEOUT, TimeUnit.SECONDS)
                .readTimeout(READ_TIMEOUT, TimeUnit.SECONDS)
                .writeTimeout(WRITE_TIMEOUT, TimeUnit.SECONDS)
                .addInterceptor(new HeaderInterceptor()) //   header
                .addInterceptor(new LoggingInterceptor())  //        ,   release    
                .sslSocketFactory(customHttpsTrust.sSLSocketFactory, customHttpsTrust.x509TrustManager)// https   
                .build();
3,Retrofit構成
       static {
        retrofit = new Retrofit.Builder()
                .baseUrl(ApiService.BASE_URL)//   baseUrl
                .client(OkHttpHelper.getClient())
                .addConverterFactory(StringConverterFactory.create()) //String   
                .addConverterFactory(GsonConverterFactory.create())
                .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
                .validateEagerly(true)
                .build();
    }
Restfulインタフェース
demoでバックグラウンドから返される標準データを例にとると、resultobjの場合:
{
      "state":1,
      "msg":"success",
      "result":{}
  }
resultが配列の場合:
{
      "state":1,
      "msg":"success",
      "result":[]
  }
このうちstateが1の場合は業務処理に成功し,データが正しいことを示す.逆に業務処理に誤りがあった場合はmsgで提示する.次のように設定されます.
public class HttpResponseResult {

    private static final int SUCCESS_STATUS = 1;
    private String msg;
    private Integer state;
    private T result;

    public boolean isSuccess() {
        return state != null && state == SUCCESS_STATUS;
    }

    public String getMsg() {
        return msg;
    }

    public Integer getState() {
        return state;
    }

    public T getResult() {
        return result;
    }

    @Override
    public String toString() {
        return "HttpResponse{" +
                "msg='" + msg + '\'' +
                ", state=" + state +
                ", result=" + result +
                '}';
    }
}
Objectの要求:
    /**
     *  post test
     * @param map
     * @return
     */
    @POST("/muses-rest/java/rest/viewlogistics/"+CHANEL)
    Observable> getLogisticsInfo(@Body Map map);
リクエストの開始:
 Map map = new HashMap<>();
 map.put("logisticsid", 20);
 map.put("logisticsno", "1000817443587");
 ServiceManager
         .getApiService()
   .getLogisticsInfo(map)
                        .compose(MainActivity.this.>bindToLifecycle())
                        .compose(TransformerHelper.transformer())
                        .compose(new DialogTransformer(MainActivity.this).>showDialog())
                        .subscribe(new CommonObserver() {
             @Override
             protected void onSuccess(LogisticsInfo logisticsInfo) {
                 Logger.e(logisticsInfo.toString());
             }
         });
Listの要求:
    @POST("/muses-rest/java/rest/viewlogistics/"+CHANEL)
    Observable> getLogisticsInfo(@Body Map map);
リクエストの開始:
ServiceManager
        .getApiService()
        .testGet2()
      .compose(MainActivity.this.>>bindToLifecycle())
                        .compose(TransformerHelper.>transformer())
                        .compose(new DialogTransformer(MainActivity.this).>>showDialog())
                        .subscribe(new CommonObserver>() {
            @Override
            protected void onSuccess(List stringList) {
                String[] str = stringList.toArray(new String[stringList.size()]);
                Logger.e(Arrays.toString(str));
            }
        });
3つのcomposeオペレータの順序が乱れないように注意してください.そうしないと、異常が発生します.内
 .compose(MainActivity.this.>>bindToLifecycle())
現在のActivityにバインドされ、ActivityはRxAppCompatActivityまたはRxActivityを継承する必要があります.独自のBaseActivityがある場合は、BaseActivityを継承させます.Fragment類似.
.compose(TransformerHelper.>transformer())
要求結果を処理する、すなわちHttpResponseResultからTを取り出す.
 .compose(new DialogTransformer(MainActivity.this).>showDialog())
ProgressDialogを操作し、そのライフサイクルはリクエスト全体を伴い、不要な場合は追加しないことができます.
一般に要求が成功するとデータ処理が行われ、失敗するとToastがユーザに提示され、CommonObserverでエラーが処理され、自動的にToastがポップアップされ、Toastをポップアップする必要がなければCommonObserveronFailed(HttpResponseException responseException)メソッドが書き換えられる.異なるビジネスロジックエラーに対して異なる処理を行う必要がある場合は、responseException.getStatus()を用いてエラーコードを得て処理すればよい.
非Restfulインタフェース
非Restfulインタフェース用は比較的少ない可能性があるため、それを整理せず、1つの実装のみを提供しているが、もちろん、プロジェクトで非Restfulインタフェース用が多い場合はパッケージ化したほうがよい.
ServiceManager
       .getApiService()
       .testGet1()
       .compose(SchedulerTransformer.transformer())//    
       .compose(MainActivity.this.bindToLifecycle())//      ,      
       .compose(new DialogTransformer(MainActivity.this).transformer())//progressDialog
       .subscribe(new Observer() {
           @Override
           public void onSubscribe(Disposable d) {
           }
           @Override
           public void onNext(String s) {
               Logger.e(s);
           }
           @Override
           public void onError(Throwable e) {
               Logger.e(e.toString());
           }
           @Override
           public void onComplete() {
           }
       });
ダウンロード操作
 final DownloadHelper downloadHelper = new DownloadHelper(url, dirPath, fileName);

        downloadHelper.downloadFile(new DownloadListener() {
            @Override
            public void update(long bytesRead, long contentLength) {
                Logger.e("----bytesRead=" + bytesRead);
                Logger.e("----contentLength=" + contentLength);
                progressDialog.setProgress((int) ((100 * bytesRead) / contentLength));
            }

            @Override
            public void onSuccess(File file) {
                progressDialog.cancel();
                Logger.e(file.getAbsolutePath() + "----" + file.length());
            }

            @Override
            public void onFailure(Throwable t) {
                progressDialog.cancel();
                Logger.e("----" + t.toString());
            }
        });
ダウンロードのキャンセル
  downloadHelper.cancelDownload();