Fix bug in request handling when incoming requests are attached to an existing response and the response is generated by directly accessing the res.servletResponse HttpServletResponse instance.
This commit is contained in:
parent
a635964fc8
commit
33fac6be68
3 changed files with 31 additions and 19 deletions
|
@ -493,11 +493,11 @@ public final class ResponseTrans extends Writer implements Serializable {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Allow to directly set the byte array for the response. Calling this more than once will
|
* Allow to directly set the byte array for the response. Calling this more than once will
|
||||||
* overwrite the previous output. We take a generic object as parameter to be able to
|
* overwrite the previous output.
|
||||||
* generate a better error message, but it must be byte[].
|
* @param bytes an arbitrary byte array
|
||||||
*/
|
*/
|
||||||
public void writeBinary(byte[] what) {
|
public void writeBinary(byte[] bytes) {
|
||||||
response = what;
|
response = bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -649,6 +649,11 @@ public final class ResponseTrans extends Writer implements Serializable {
|
||||||
// there's no point in closing the response buffer
|
// there's no point in closing the response buffer
|
||||||
HttpServletResponse res = reqtrans.getServletResponse();
|
HttpServletResponse res = reqtrans.getServletResponse();
|
||||||
if (res != null && res.isCommitted()) {
|
if (res != null && res.isCommitted()) {
|
||||||
|
// response was committed using HttpServletResponse directly. We need
|
||||||
|
// set response to null and notify waiters in order to let attached
|
||||||
|
// requests know they can't reuse this response.
|
||||||
|
response = null;
|
||||||
|
notifyAll();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -664,7 +669,8 @@ public final class ResponseTrans extends Writer implements Serializable {
|
||||||
|
|
||||||
boolean encodingError = false;
|
boolean encodingError = false;
|
||||||
|
|
||||||
// only close if the response hasn't been closed yet
|
// only close if the response hasn't been closed yet, and if no
|
||||||
|
// response was generated using writeBinary().
|
||||||
if (response == null) {
|
if (response == null) {
|
||||||
// if debug buffer exists, append it to main buffer
|
// if debug buffer exists, append it to main buffer
|
||||||
if (contentType != null &&
|
if (contentType != null &&
|
||||||
|
@ -747,7 +753,7 @@ public final class ResponseTrans extends Writer implements Serializable {
|
||||||
* @return the response body
|
* @return the response body
|
||||||
*/
|
*/
|
||||||
public byte[] getContent() {
|
public byte[] getContent() {
|
||||||
return (response == null) ? new byte[0] : response;
|
return response;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -720,6 +720,14 @@ public final class Application implements Runnable {
|
||||||
|
|
||||||
if (ev != null) {
|
if (ev != null) {
|
||||||
res = ev.attachHttpRequest(req);
|
res = ev.attachHttpRequest(req);
|
||||||
|
if (res != null) {
|
||||||
|
// we can only use the existing response object if the response
|
||||||
|
// wasn't written to the HttpServletResponse directly.
|
||||||
|
res.waitForClose();
|
||||||
|
if (res.getContent() == null) {
|
||||||
|
res = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (res == null) {
|
if (res == null) {
|
||||||
|
@ -752,8 +760,6 @@ public final class Application implements Runnable {
|
||||||
} catch (UnsupportedEncodingException uee) {
|
} catch (UnsupportedEncodingException uee) {
|
||||||
logError("Unsupported response encoding", uee);
|
logError("Unsupported response encoding", uee);
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
res.waitForClose();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -345,20 +345,20 @@ public abstract class AbstractServletClient extends HttpServlet {
|
||||||
res.setContentLength(hopres.getContentLength());
|
res.setContentLength(hopres.getContentLength());
|
||||||
res.setContentType(hopres.getContentType());
|
res.setContentType(hopres.getContentType());
|
||||||
|
|
||||||
if ("HEAD".equalsIgnoreCase(req.getMethod())) {
|
if (!"HEAD".equalsIgnoreCase(req.getMethod())) {
|
||||||
return;
|
byte[] content = hopres.getContent();
|
||||||
}
|
if (content != null) {
|
||||||
|
|
||||||
try {
|
try {
|
||||||
OutputStream out = res.getOutputStream();
|
OutputStream out = res.getOutputStream();
|
||||||
|
out.write(content);
|
||||||
out.write(hopres.getContent());
|
|
||||||
out.flush();
|
out.flush();
|
||||||
} catch (Exception iox) {
|
} catch (Exception iox) {
|
||||||
log("Exception in writeResponse: " + iox);
|
log("Exception in writeResponse: " + iox);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void sendError(HttpServletResponse response, int code, String message)
|
void sendError(HttpServletResponse response, int code, String message)
|
||||||
throws IOException {
|
throws IOException {
|
||||||
|
|
Loading…
Add table
Reference in a new issue