Mig*_*uel 8 android request http-status-code-304 android-volley jsonobject
玩弄Volley库时,我注意到在进行POST时JsonObjectRequest,如果服务器返回代码304或200且响应中没有数据,则(response.data)Volley将其解释为错误响应,而不是成功.
我设法通过Response<JSONObject> parseNetworkResponse(NetworkResponse response)在类中的方法中添加几行代码来解决它JsonObjectRequest.java.
@Override
protected Response<JSONObject> parseNetworkResponse(NetworkResponse response) {
try {
if (!response.notModified) {// Added for 304 response
String jsonString = new String(response.data,
HttpHeaderParser.parseCharset(response.headers));
return Response.success(new JSONObject(jsonString),
HttpHeaderParser.parseCacheHeaders(response));
} else // Added for 304 response
return Response.success(new JSONObject(),HttpHeaderParser.parseCacheHeaders(response));
} catch (UnsupportedEncodingException e) {
Log.v("Volley", "UnsupportedEncodingException " + response.statusCode);
if (response.statusCode == 200)// Added for 200 response
return Response.success(new JSONObject(), HttpHeaderParser.parseCacheHeaders(response));
else
return Response.error(new ParseError(e));
} catch (JSONException je) {
Log.v("Volley", "JSONException " + response.statusCode);
if (response.statusCode == 200)// Added for 200 response
return Response.success(new JSONObject(),HttpHeaderParser.parseCacheHeaders(response));
else
return Response.error(new ParseError(je));
}
}
Run Code Online (Sandbox Code Playgroud)
这是解决这个问题的最佳方法吗?
谢谢!
编辑
检查课程BasicNetwork.java我意识到Volley通过询问是否检查响应是否没有数据httpResponse.getEntity() != null.
// Some responses such as 204s do not have content. We must check.
if (httpResponse.getEntity() != null) {
responseContents = entityToBytes(httpResponse.getEntity());
} else {// Add 0 byte response as a way of honestly representing a
// no-content request.
responseContents = new byte[0];
}
Run Code Online (Sandbox Code Playgroud)
但问题仍然是Volley尝试response.data == new byte[0]在parseNetworkResponse方法中创建新字符串时发生的JSONException.
Miguel-只有在成功响应的情况下才会调用此方法吗?
对于所有状态代码<200或状态代码> 200,volley调用parseNetworkError(VolleyError volleyError)而不是parseNetworkResponse(NetworkResponse response)方法.看这里 -
行号-118-120
if (statusCode < 200 || statusCode > 299) {
throw new IOException();
}
Run Code Online (Sandbox Code Playgroud)
和相应的catch块行号 - 128 -151
catch (IOException e) {
int statusCode = 0;
NetworkResponse networkResponse = null;
if (httpResponse != null) {
statusCode = httpResponse.getStatusLine().getStatusCode();
} else {
throw new NoConnectionError(e);
}
VolleyLog.e("Unexpected response code %d for %s", statusCode, request.getUrl());
if (responseContents != null) {
networkResponse = new NetworkResponse(statusCode, responseContents,
responseHeaders, false);
if (statusCode == HttpStatus.SC_UNAUTHORIZED ||
statusCode == HttpStatus.SC_FORBIDDEN) {
attemptRetryOnException("auth",
request, new AuthFailureError(networkResponse));
} else {
// TODO: Only throw ServerError for 5xx status codes.
throw new ServerError(networkResponse);
}
} else {
throw new NetworkError(networkResponse);
}
}
Run Code Online (Sandbox Code Playgroud)
如果要覆盖此行为,可以在BasicNetwork.java-> performRequest方法中添加特定于状态代码的实现.
编辑:所以它不是因为状态代码而是因为空响应.好吧,我认为你正在做正确的事情来实现你的自定义Request类.Volley附带了一些易于使用的预定义流行类型请求,但您可以随时创建自己的.而不是基于状态代码的实现,我宁愿在反序列化之前检查以下字符串是否为空 -
String jsonString = new String(response.data,
HttpHeaderParser.parseCharset(response.headers));
if (!jsonString .isEmpty()) {
return Response.success(new JSONObject(jsonString),
HttpHeaderParser.parseCacheHeaders(response));
}
else {
return Response.success(new JSONObject(),
HttpHeaderParser.parseCacheHeaders(response));
}
Run Code Online (Sandbox Code Playgroud)
**没有测试过这个,但你明白了:)
| 归档时间: |
|
| 查看次数: |
7963 次 |
| 最近记录: |