Volley + OkHttp3 + Gson 組合的簡單網路請求封裝
阿新 • • 發佈:2019-01-01
1. Volley —— Google出品的android平臺輕量級網路庫
優點:擴充套件性強,請求佇列管理
基本介紹:http://blog.csdn.net/itachi85/article/details/51043704
github映象: https://github.com/mcxiaoke/android-volley
2. okhttp —— Square出品的java網路庫,android4.4以後已作為預設的HTTP連線實現
優點:支援SPDY,連線池,傳輸效率的各種優化
基本介紹:http://blog.csdn.net/itachi85/article/details/51142486
原始碼:https: //github.com/square/okhttp
官方wiki:https://github.com/square/okhttp/wiki
3. Volley + OkHttp 結合
由於 Volley 和 OKHttp 各有優缺點,Volley 不支援 HTTPS,而 OKHttp 支援 HTTPS。Volley的擴充套件性又非常強,因此我們可以將 Volley 和 OKHTTP結合使用。
4. 新增依賴
// Volley
compile 'com.android.volley:volley:1.0.0'
// okhttp
compile 'com.squareup.okhttp3:okhttp:3.4.1'
compile 'com.squareup.okhttp3:okhttp-urlconnection:3.4.1'
// gson
compile 'com.google.code.gson:gson:2.7'
5. AppConfig.java —— 全域性Application的配置
package com.qianxingzhe.mynetwork.app;
import android.app.Application;
import com.android.volley.RequestQueue;
import com.qianxingzhe.mynetwork.network.RequestManager;
/**
* Created by lunyi.yly on 16/9/5.
*/
public class AppConfig extends Application {
private static AppConfig instance;
@Override
public void onCreate() {
super.onCreate();
initAppConfig();
initNetWork();
}
private void initNetWork() {
if (RequestManager.getRequestQueueNoThrowable() == null) {
RequestManager.init(this);
}
}
private void initAppConfig() {
if (instance == null) {
instance = this;
}
}
public static Application getApp() {
return instance;
}
public static RequestQueue requestQueue() {
return RequestManager.getRequestQueue();
}
}
6. OkHttpStack
package com.qianxingzhe.mynetwork.network;
import com.android.volley.toolbox.HurlStack;
import java.io.IOException;
import java.net.HttpURLConnection;
import java.net.URL;
import java.security.KeyStore;
import java.util.Arrays;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import javax.net.ssl.TrustManagerFactory;
import javax.net.ssl.X509TrustManager;
import okhttp3.OkHttpClient;
import okhttp3.OkUrlFactory;
/**
* Created by lunyi.yly on 16/9/5.
*/
public class OkHttpStack extends HurlStack {
private final OkUrlFactory okUrlFactory;
public OkHttpStack() {
this(new OkUrlFactory(getUnsafeOkHttpClient()));
}
public OkHttpStack(OkUrlFactory okUrlFactory) {
if (okUrlFactory == null) {
throw new NullPointerException("Client must not be null.");
}
this.okUrlFactory = okUrlFactory;
}
@Override
protected HttpURLConnection createConnection(URL url) throws IOException {
return okUrlFactory.open(url);
}
/**
* 支援HTTPS。按下面的註釋進行
*
* @return
*/
private static OkHttpClient getUnsafeOkHttpClient() {
try {
/**
* 讀取公鑰證書內容
* 首先要把你的https公鑰證書通過瀏覽器或者其他方法匯出,放進android資源目錄assets下。
* 然後AppConfig這個類是繼承了Application的,android啟動的時候會先執行它,getApp是一個單例模式的實現
*/
// 配置HTTPS時需要開啟下面的註釋
// InputStream inputStream = AppConfig.getApp().getAssets().open("https.cer");
//
// CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
//
// KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
// keyStore.load(null);
//
// int index = 0;
// String certificateAlias = Integer.toString(index++);
// keyStore.setCertificateEntry(certificateAlias, certificateFactory.generateCertificate(inputStream));
TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance(
TrustManagerFactory.getDefaultAlgorithm());
// 配置HTTPS時需要把下面的註釋開啟
// trustManagerFactory.init(keyStore);
// 配置HTTPS時需要把下面這句註釋掉
trustManagerFactory.init((KeyStore) null);
TrustManager[] trustManagers = trustManagerFactory.getTrustManagers();
if (trustManagers.length != 1 || !(trustManagers[0] instanceof X509TrustManager)) {
throw new IllegalStateException("Unexpected default trust managers:"
+ Arrays.toString(trustManagers));
}
X509TrustManager trustManager = (X509TrustManager) trustManagers[0];
SSLContext sslContext = SSLContext.getInstance("TLS");
sslContext.init(null, new TrustManager[]{trustManager}, null);
SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
OkHttpClient client = new OkHttpClient
.Builder()
.sslSocketFactory(sslSocketFactory, trustManager)
.build();
return client;
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
7. RequestManager
package com.qianxingzhe.mynetwork.network;
import android.content.Context;
import com.android.volley.RequestQueue;
import com.android.volley.toolbox.Volley;
/**
* Created by lunyi.yly on 16/9/5.
*/
public class RequestManager {
private static RequestQueue mRequestQueue;
private RequestManager() {
}
public static void init(Context context) {
if (mRequestQueue == null) {
mRequestQueue = Volley.newRequestQueue(context, new OkHttpStack());
}
}
/**
* @return instance() of the queue
* @throws IllegalStateException if init has not yet been called
*/
public static RequestQueue getRequestQueue() {
if (mRequestQueue != null) {
return mRequestQueue;
} else {
throw new IllegalStateException("Not initialized");
}
}
/**
* @return instance() of the queue
* @throws IllegalStateException if init has not yet been called
*/
public static RequestQueue getRequestQueueNoThrowable() {
return mRequestQueue;
}
}
9. MyJsonObjectRequest
package com.qianxingzhe.mynetwork.network;
import android.util.Log;
import android.widget.Toast;
import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.android.volley.toolbox.JsonObjectRequest;
import com.qianxingzhe.mynetwork.BuildConfig;
import com.qianxingzhe.mynetwork.app.AppConfig;
import org.json.JSONObject;
import java.util.Map;
/**
* Created by lunyi.yly on 16/9/6.
*/
public class MyJsonObjectRequest {
/**
* 請求型別。如: GET,POST等
*/
private int method;
/**
* 請求的URL
*/
private String url;
/**
* 請求的引數
*/
private JSONObject requestParameter;
/**
* 請求成功的響應
*/
private RequestNetWork requestNetWork;
public MyJsonObjectRequest(int method, String url, Map<String, Object> parameter, RequestNetWork requestNetWork) {
this.method = method;
this.url = url;
this.requestNetWork = requestNetWork;
initRequestParameter(parameter);
createJsonObjectRequest();
}
private void initRequestParameter(Map<String, Object> parameter) {
if (parameter == null) {
return;
}
this.requestParameter = new JSONObject(parameter);
}
private void createJsonObjectRequest() {
JsonObjectRequest mJsonObjectRequest = new JsonObjectRequest(
method,
url,
requestParameter,
new Response.Listener<JSONObject>() {
@Override
public void onResponse(JSONObject response) {
if (BuildConfig.DEBUG) {
Log.e("TAG", response.toString());
}
requestNetWork.onSuccess(response);
}
},
new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
if (BuildConfig.DEBUG) {
Log.e("TAG", error.getMessage(), error);
}
Toast.makeText(AppConfig.getApp(), "網路請求失敗", Toast.LENGTH_SHORT).show();
}
}
);
AppConfig.requestQueue().add(mJsonObjectRequest);
}
public interface RequestNetWork {
void onSuccess(JSONObject response);
}
}
10. 使用示例
MyJsonObjectRequest mRequest = new MyJsonObjectRequest(
Request.Method.POST,
"http://api.1-blog.com/biz/bizserver/article/list.do",
null,
new MyJsonObjectRequest.RequestNetWork() {
@Override
public void onSuccess(JSONObject response) {
Gson mGson = new Gson();
Article article = mGson.fromJson(response.toString(), Article.class);
Log.e("TAG", article.getDetail().get(0).getTitle());
}
}
);
11. AndroidManifest設定
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.qianxingzhe.mynetwork">
<uses-permission android:name="android.permission.INTERNET"/>
<application
android:name=".app.AppConfig"
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
</application>
</manifest>