Java 如何在不使用HttpEntity的情况下读取它?
我有Java 如何在不使用HttpEntity的情况下读取它?,java,android,httpresponse,Java,Android,Httpresponse,我有org.apache.http.HttpResponse对象,我在代码中的不同位置使用它。其中一个地方是用来伐木的 问题是,当我运行以下日志代码时: HttpEntity entity = response.getEntity(); try { String content = Base64.encodeToString( EntityUtils.toByteArray(entity), Base64.DEFAULT); sb.append(conte
org.apache.http.HttpResponse
对象,我在代码中的不同位置使用它。其中一个地方是用来伐木的
问题是,当我运行以下日志代码时:
HttpEntity entity = response.getEntity();
try {
String content = Base64.encodeToString(
EntityUtils.toByteArray(entity), Base64.DEFAULT);
sb.append(content + "\r\n");
} catch (Exception e) {
sb.append("\r\n\r\n====EXCEPTION=====\r\n" + e.toString()
+ "\r\n");
}
然后我尝试读取实际处理代码中的条目内容,这会导致代码引发以下异常:
java.lang.IllegalStateException: Content has been consumed
我的问题是:如何读取实体而不在日志代码中使用它
更新
下面是我用来将httpresponse转换为字符串的函数的完整代码:
static String toString(org.apache.http.HttpResponse response) {
try {
if (response == null) {
return "null";
}
StringBuilder sb = new StringBuilder();
sb.append("==============BEGIN HttpResponse================\r\n");
StatusLine sl = response.getStatusLine();
if (sl == null) {
sb.append("status line is null\r\n");
} else {
sb.append(String.format("%s %s\r\n", sl.getStatusCode(),
sl.getReasonPhrase()));
}
for (Header h : response.getAllHeaders()) {
if (h == null) {
sb.append("header is null\r\n");
continue;
}
sb.append(String.format("%s: %s\r\n", h.getName(), h.getValue()));
}
sb.append("\r\r\r\n");
HttpEntity entity = response.getEntity();
if (entity == null) {
sb.append("content is null");
} else {
try {
String content = Base64.encodeToString(
EntityUtils.toByteArray(entity), Base64.DEFAULT);
sb.append(content + "\r\n");
} catch (Exception e) {
sb.append("\r\n\r\n====EXCEPTION=====\r\n" + e.toString()
+ "\r\n");
}
}
sb.append("\r\n==============END HttpResponse================\r\n");
return sb.toString();
} catch (Exception e) {
return e.toString();
}
}
嗯。因此,我最终要做的是实现自己的HttpEntity类,而不仅仅是使用
response.setEntity(…)
替换以前的实体。该类将结果存储为二进制数组,并根据需要多次返回该结果。它可能会给您带来一些性能问题,但会起作用:
带有日志记录的HttpClient示例
private CloseableHttpResponse invoke(HttpRequestBase http) {
try {
CloseableHttpResponse response = client.execute(http);
if (http instanceof HttpPost) {
InputStream inputStream = ((HttpPost) http).getEntity().getContent();
String body = IOUtils.toString(inputStream, Charset.defaultCharset());
HttpEntity respBody = response.getEntity();
String responseBody = StreamUtils.copyToString(respBody.getContent(), Charset.defaultCharset());
response.setEntity(new StringEntity(responseBody));
LOG.info(String.format("Sending request: [%s] %s => [%s] \nPayload:\n%s \nResponse:\n%s", http.getMethod(), http.getURI(), response.getStatusLine(), body, responseBody));
} else {
LOG.info(String.format("Sending request: [%s] %s => [%s]", http.getMethod(), http.getURI(), response.getStatusLine()));
}
return response;
} catch (IOException e) {
throw new RuntimeException("HTTP request failed: " + http.toString(), e);
}
}
主要思想如下:1.进行http调用
2.复制到响应正文的字符串:
HttpEntity respBody = response.getEntity();
String responseBody = StreamUtils.copyToString(respBody.getContent(), Charset.defaultCharset());
response.setEntity(新的StringEntity(ResponseBy))代码>
此示例适用于小型测试框架,但不确定它是否适用于生产应用程序请在“response.getEntity();”之前发布代码。您可以尝试
标记
实体inputstream,然后重置它,但我不确定它是否确实可标记