在使用Volly開源框架時遇到了一個問題塞关,報了錯誤只有一個 SERVERERROR 蜒犯, 那怎么辦呢,找谷哥咯硫戈,貼上搜索下發(fā)現(xiàn)是服務(wù)器的響應的一個錯誤锰什,最有可能的4xx或5xx HTTP狀態(tài)代碼。
一般我們使用Volly打印日志是用 ** Log.e("VolleyError---", volleyError.getMessage(), volleyError);**
打印出的錯誤信息非常有限丁逝,如下面一些
null
com.android.volley.ServerError
at com.android.volley.toolbox.BasicNetwork.performRequest(BasicNetwork.java:145)
at com.android.volley.NetworkDispatcher.run(NetworkDispatcher.java:105)
以及 Volley框架打印的錯誤
BasicNetwork.performRequest: Unexpected response code 500 for
這些也僅只能判斷是服務(wù)器端出現(xiàn)問題汁胆,但是究竟是什么原因,請求的參數(shù)不正確霜幼?還是服務(wù)器端哪里不對了嫩码?憑借以上信息個人一般無法判斷。
判斷不出罪既,那只能想辦法了铸题,從哪突破呢,既然是 VolleyError 拋出錯誤琢感,那我們來分析一下拋出錯誤的VolleyError類吧丢间。
這里開始推輪子,貼源碼
public class VolleyError extends java.lang.Exception {
public final com.android.volley.NetworkResponse networkResponse;
public VolleyError() { /* compiled code */ }
public VolleyError(com.android.volley.NetworkResponse response) { /* compiled code */ }
public VolleyError(java.lang.String exceptionMessage) { /* compiled code */ }
public VolleyError(java.lang.String exceptionMessage, java.lang.Throwable reason) { /* compiled code */ }
public VolleyError(java.lang.Throwable cause) { /* compiled code */ }
}
看到這里驹针,我們猜測 networkResponse 這個對象含有返回的全部消息烘挫。
再打開 NetworkResponse 這個類的源碼。
public class NetworkResponse {
/**
* Creates a new network response.
* @param statusCode the HTTP status code
* @param data Response body
* @param headers Headers returned with this response, or null for none
* @param notModified True if the server returned a 304 and the data was already in cache
*/
public NetworkResponse(int statusCode, byte[] data, Map<String, String> headers,
boolean notModified) {
this.statusCode = statusCode;
this.data = data;
this.headers = headers;
this.notModified = notModified;
}
public NetworkResponse(byte[] data) {
this(HttpStatus.SC_OK, data, Collections.<String, String>emptyMap(), false);
}
public NetworkResponse(byte[] data, Map<String, String> headers) {
this(HttpStatus.SC_OK, data, headers, false);
}
/** The HTTP status code. */
public final int statusCode;
/** Raw data from this response. */
public final byte[] data;
/** Response headers. */
public final Map<String, String> headers;
/** True if the server returned a 304 (Not Modified). */
public final boolean notModified;
}
注意看注釋柬甥,@param data Response body 于是我們知道data是回應報文的包體內(nèi)容饮六,只要把data解碼并顯示出來,那么就有可能看到更詳細的錯誤信息苛蒲,最起碼是一段HTML文檔卤橄。
接下來我們只需要把data解碼獲取:
new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError volleyError) {
Log.e("VolleyError---", volleyError.getMessage(), volleyError);
byte[] htmlBodyBytes = volleyError.networkResponse.data; //回應的報文的包體內(nèi)容
Log.e("VolleyError body---->", new String(htmlBodyBytes), volleyError);
return;
}
}
經(jīng)過這樣改造后撤防,logcat中的錯誤輸出信息就變得很詳細和清晰了虽风。
Volley的異常列表:
- AuthFailureError:如果在做一個HTTP的身份驗證,可能會發(fā)生這個錯誤寄月。
- NetworkError:Socket關(guān)閉辜膝,服務(wù)器宕機,DNS錯誤都會產(chǎn)生這個錯誤漾肮。
- NoConnectionError:和NetworkError類似厂抖,這個是客戶端沒有網(wǎng)絡(luò)連接。
- ParseError:在使用JsonObjectRequest或JsonArrayRequest時克懊,如果接收到的JSON是畸形忱辅,會產(chǎn)生異常七蜘。
- SERVERERROR:服務(wù)器的響應的一個錯誤,最有可能的4xx或5xx HTTP狀態(tài)代碼墙懂。
- TimeoutError:Socket超時橡卤,服務(wù)器太忙或網(wǎng)絡(luò)延遲會產(chǎn)生這個異常。默認情況下损搬,Volley的超時時間為2.5秒碧库。如果得到這個錯誤可以使用RetryPolicy。