我有一个HTTP GET servlet设置,它返回JSON编码的DICOM图像(医学图像)但是我在返回响应时内存不足,因为JSON输出流最终复制整个事件,如下面粗体显示的异常堆栈帧。
错误| 2016-03-29 14:08:45,068 | - 线程中的异常 “http-bio-8080-exec-1”ERROR | 2016-03-29 14:08:45,068 | - java.lang.OutOfMemoryError:Java堆空间错误| 2016年3月29日 14:08:45,068 | - 在 java.util.Arrays.copyOf (Arrays.java:2882)错误 | 2016-03-29 14:08:45,068 | - 在 java.lang.AbstractStringBuilder.expandCapacity(AbstractStringBuilder.java:100) 错误| 2016-03-29 14:08:45,069 | - 在 java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:390) 错误| 2016-03-29 14:08:45,069 | - 在 java.lang.StringBuffer.append(StringBuffer.java:224)错误| 2016-03-29 14:08:45,069 | - 在 java.io.StringWriter.write(StringWriter.java:84)错误| 2016年3月29日 14:08:45,069 | - 在 org.json.JSONObject.writeValue(JSONObject.java:1562)错误| 2016-03-29 14:08:45,069 | - 在 org.json.JSONArray.write(JSONArray.java:929)错误| 2016年3月29日 14:08:45,069 | - 在 org.json.JSONObject.writeValue(JSONObject.java:1553)错误| 2016-03-29 14:08:45,069 | - 在 org.json.JSONObject.write(JSONObject.java:1626)错误| 2016年3月29日 14:08:45,069 | - 在 org.json.JSONObject.writeValue(JSONObject.java:1551)错误| 2016-03-29 14:08:45,069 | - 在 org.json.JSONObject.write(JSONObject.java:1609)错误| 2016年3月29日 14:08:45,069 | - 在 org.json.JSONObject.toString(JSONObject.java:1420)错误| 2016年3月29日 14:08:45,069 | - 在 org.json.JSONObject.toString(JSONObject.java:1397)错误| 2016年3月29日 14:08:45,069 | - 在java.lang.String.valueOf(String.java:2826) 错误| 2016-03-29 14:08:45,069 | - 在 org.apache.catalina.connector.CoyoteWriter.print(CoyoteWriter.java:248) 错误| 2016-03-29 14:08:45,069 | - 在 com.tiasl.ImageViewerServlet.doGet(ImageViewerServlet.java:196) 错误| 2016-03-29 14:08:45,069 | - 在 javax.servlet.http.HttpServlet.service(HttpServlet.java:621)错误| 2016-03-29 14:08:45,069 | - 在 javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
要创建输出流,我使用响应编写器,如下所示:
// Get the printwriter object from response to write the required json object to the output stream
PrintWriter out = resp.getWriter();
// Assuming your json object is **jsonObject**, perform the following, it will return your json object
out.print(jsonObj);
那么,有没有其他更有效的方法来流式传输相当大的JSON对象而不会耗尽内存?这是一个非常令人沮丧的情况,因为它会影响我的并发用户数量。我们已经拥有2台服务器,而且由于JSON最终是文本,如何以块的形式进行流式传输?
此应用程序发送500KB到200MB的医学图像。其中大多数将约为1MB。我们使用Java应用程序服务器端点将图像流式传输回网页。这是我们的第一个非优化草案,所以我们想要一个简单的方法。
我们使用JS请求图像:
xhr = new XMLHttpRequest();
xhr.open("GET", parsedId.url + "?quality=" + parsedId.requestedQuality + "&v=" + startTime, false);
xhr.responseType = 'text';
xhr.timeout = timeout;
xhr.send();
if (!(xhr.status === 200 || xhr.status === 206)) {
throw Error(xhr.status + " " + xhr.statusText + ": " + parsedId.url);
}
endTime = Date.now();
stats.downloadTime += (endTime - startTime);
stats.fileSize = xhr.responseText.length;
var jsonData = JSON.parse(xhr.responseText);