天天看點

Android Retrofit 2.0 使用-補充篇Retrofit配置接口參數微信公衆号關于作者

推薦閱讀,猛戳:

1、Android MVP 執行個體

2、Android Retrofit 2.0使用

3、RxJava

4、RxBus

5、Android MVP+Retrofit+RxJava實踐小結

之前分享的Android Retrofit 2.0 使用,屬于基本的使用,實際開發還遠遠不夠,是以對其補充,主要在Retrofit配置和接口參數。

Retrofit配置

添加依賴

app/build.gradle

首先Builder(),得到OkHttpClient.Builder對象builder

OkHttpClient.Builder builder = new OkHttpClient.Builder();
           

Log資訊攔截器

Debug可以看到,網絡請求,列印Log資訊,釋出的時候就不需要這些log

1、添加依賴

app/build.gradle

2、Log資訊攔截器

if (BuildConfig.DEBUG) {
    // Log資訊攔截器
    HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor();
    loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
    //設定 Debug Log 模式
    builder.addInterceptor(loggingInterceptor);
}
           

緩存機制

無網絡時,也能顯示資料

File cacheFile = new File(DemoApplication.getContext().getExternalCacheDir(), "WuXiaolongCache");
Cache cache = new Cache(cacheFile,  *  * );
Interceptor cacheInterceptor = new Interceptor() {
    @Override
    public Response intercept(Chain chain) throws IOException {
        Request request = chain.request();
        if (!AppUtils.networkIsAvailable(DemoApplication.getContext())) {
            request = request.newBuilder()
                    .cacheControl(CacheControl.FORCE_CACHE)
                    .build();
        }
        Response response = chain.proceed(request);
        if (AppUtils.networkIsAvailable(DemoApplication.getContext())) {
            int maxAge = ;
            // 有網絡時 設定緩存逾時時間0個小時
            response.newBuilder()
                    .header("Cache-Control", "public, max-age=" + maxAge)
                    .removeHeader("WuXiaolong")// 清除頭資訊,因為伺服器如果不支援,會傳回一些幹擾資訊,不清除下面無法生效
                    .build();
        } else {
            // 無網絡時,設定逾時為4周
            int maxStale =  *  *  * ;
            response.newBuilder()
                    .header("Cache-Control", "public, only-if-cached, max-stale=" + maxStale)
                    .removeHeader("nyn")
                    .build();
        }
        return response;
    }
};
builder.cache(cache).addInterceptor(cacheInterceptor);
           

公共參數

可能接口有某些參數是公共的,不可能一個個接口都去加吧

//公共參數
Interceptor addQueryParameterInterceptor = new Interceptor() {
    @Override
    public Response intercept(Chain chain) throws IOException {
        Request originalRequest = chain.request();
        Request request;
        String method = originalRequest.method();
        Headers headers = originalRequest.headers();
        HttpUrl modifiedUrl = originalRequest.url().newBuilder()
                // Provide your custom parameter here
                .addQueryParameter("platform", "android")
                .addQueryParameter("version", "1.0.0")              
                .build();
        request = originalRequest.newBuilder().url(modifiedUrl).build();
        return chain.proceed(request);
    }
};
//公共參數
builder.addInterceptor(addQueryParameterInterceptor);
           

設定頭

有的接口可能對請求頭要設定

Interceptor headerInterceptor = new Interceptor() {
    @Override
    public Response intercept(Chain chain) throws IOException {
        Request originalRequest = chain.request();
        Request.Builder requestBuilder = originalRequest.newBuilder()
                .header("AppType", "TPOS")
                .header("Content-Type", "application/json")
                .header("Accept", "application/json")
                .method(originalRequest.method(), originalRequest.body());
        Request request = requestBuilder.build();
        return chain.proceed(request);
    }
};
//設定頭
builder.addInterceptor(headerInterceptor );
           

設定cookie

服務端可能需要保持請求是同一個cookie,主要看各自需求

1、app/build.gradle

2、設定cookie

CookieManager cookieManager = new CookieManager();
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_ALL);
builder.cookieJar(new JavaNetCookieJar(cookieManager));
           

設定逾時和重連

希望逾時時能重連

//設定逾時
 builder.connectTimeout(, TimeUnit.SECONDS);
 builder.readTimeout(, TimeUnit.SECONDS);
 builder.writeTimeout(, TimeUnit.SECONDS);
 //錯誤重連
 builder.retryOnConnectionFailure(true);
           

最後将這些配置設定給retrofit:

OkHttpClient okHttpClient = builder.build();
Retrofit retrofit = new Retrofit.Builder()
        .baseUrl(ApiStores.API_SERVER_URL)
        //設定 Json 轉換器
        .addConverterFactory(GsonConverterFactory.create())
        //RxJava 擴充卡
        .addCallAdapterFactory(RxJavaCallAdapterFactory.create())
        .client(okHttpClient)
        .build();
           

完整配置

public class AppClient {
    public static Retrofit retrofit = null;

    public static Retrofit retrofit() {
        if (retrofit == null) {
             OkHttpClient.Builder builder = new OkHttpClient.Builder();
            /**
             *設定緩存,代碼略
             */

            /**
             *  公共參數,代碼略
             */

            /**
             * 設定頭,代碼略
             */           

             /**
             * Log資訊攔截器,代碼略
             */

             /**
             * 設定cookie,代碼略
             */

             /**
             * 設定逾時和重連,代碼略
             */

            //以上設定結束,才能build(),不然設定白搭
            OkHttpClient okHttpClient = builder.build();

            retrofit = new Retrofit.Builder()
                    .baseUrl(ApiStores.API_SERVER_URL)                  
                    .client(okHttpClient)
                    .build();
        }
        return retrofit;

    }
}
           

接口參數

Path

類似這樣連結:http://wuxiaolong.me/2016/01/15/retrofit/

@GET("2016/01/15/{retrofit}")
 Call<ResponseBody> getData(@Path("retrofit") String retrofit);
           

即您傳的參數retrofit内容會替換大括号裡的内容。

Query

類似這樣連結:http://wuxiaolong.me/v1?ip=202.202.33.33&name=WuXiaolong

@GET("v1")
Call<ResponseBody> getData(@Query("ip") String ip,@Query("name") String name);
           

Field

表單送出,如登入

@FormUrlEncoded
 @POST("v1/login")
 Call<ResponseBody> userLogin(@Field("phone") String phone, @Field("password") String password);
           

傳json格式

如果參數是json格式,如:

{       
    "apiInfo": {        
        "apiName": "WuXiaolong",        
        "apiKey": "666"     
    }       
}       
           

建立Bean

public class ApiInfo {
        private ApiInfoBean apiInfo;

        public ApiInfoBean getApiInfo() {
            return apiInfo;
        }

        public void setApiInfo(ApiInfoBean apiInfo) {
            this.apiInfo = apiInfo;
        }

        public class ApiInfoBean {
            private String apiName;
            private String apiKey;
            //省略get和set方法
        }
    }
           

ApiStores

@POST("client/shipper/getCarType")
Call<ResponseBody> getData(@Body ApiInfo apiInfo);
           

代碼調用

ApiInfo apiInfo = new ApiInfo();
ApiInfo.ApiInfoBean apiInfoBean = apiInfo.new ApiInfoBean();
apiInfoBean.setApiKey("666");
apiInfoBean.setApiName("WuXiaolong");
apiInfo.setApiInfo(apiInfoBean);
//調接口
getData(apiInfo);
           

傳數組

@GET("v1/enterprise/find")
Call<ResponseBody> getData(@Query("id") String id, @Query("linked[]") String... linked);
           

代碼調用

String id="WuXiaolong";
String[] s = new String[]{"WuXiaolong"};
//調接口
getData(id, s);
           

傳檔案-單個

@Multipart
@POST("v1/create")
Call<ResponseBody> create(@Part("pictureName") RequestBody pictureName,  @Part MultipartBody.Part picture);
           

代碼調用

RequestBody pictureNameBody = RequestBody.create(MediaType.parse(AppConstants.CONTENT_TYPE_FILE), "pictureName");
File picture= new File(path);
RequestBody requestFile = RequestBody.create(MediaType.parse(AppConstants.CONTENT_TYPE_FILE), picture);
// MultipartBody.Part is used to send also the actual file name
MultipartBody.Part picturePart = MultipartBody.Part.createFormData("picture", picture.getName(), requestFile);
//調接口
create(pictureNameBody, picturePart);
           

傳檔案-多個

@Multipart
@POST("v1/create")
Call<ResponseBody> create(@Part("pictureName") RequestBody pictureName,   @PartMap Map<String, RequestBody> params);
           

代碼調用

RequestBody pictureNameBody = RequestBody.create(MediaType.parse(AppConstants.CONTENT_TYPE_FILE), "pictureName");
File picture= new File(path);
RequestBody requestFile = RequestBody.create(MediaType.parse(AppConstants.CONTENT_TYPE_FILE), picture);
Map<String, RequestBody> params = new HashMap<>();
params.put("picture\"; filename=\"" + picture.getName() + "", requestFile);
//調接口
create(pictureNameBody, params);
           

微信公衆号

我的微信公衆号:吳小龍同學,不止于技術分享,每天進步一點點,歡迎微信掃一掃關注。

Android Retrofit 2.0 使用-補充篇Retrofit配置接口參數微信公衆号關于作者

關于作者

點選檢視