Merge remote-tracking branch 'origin/jetty-9.2.x'
Conflicts: jetty-server/src/main/java/org/eclipse/jetty/server/handler/gzip/GzipHttpOutputInterceptor.java jetty-servlets/src/main/java/org/eclipse/jetty/servlets/AsyncGzipFilter.java jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/GzipContentLengthTest.java Added Interceptor chain so that double gzip interception can be prevented.
This commit is contained in:
commit
dfe799d04c
|
@ -641,6 +641,11 @@ public class HttpChannel implements Runnable, HttpOutput.Interceptor
|
|||
_written+=BufferUtil.length(content);
|
||||
sendResponse(null,content,complete,callback);
|
||||
}
|
||||
|
||||
public HttpOutput.Interceptor getNextInterceptor()
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
protected void execute(Runnable task)
|
||||
{
|
||||
|
|
|
@ -57,6 +57,7 @@ public class HttpOutput extends ServletOutputStream implements Runnable
|
|||
public interface Interceptor
|
||||
{
|
||||
void write(ByteBuffer content, boolean complete, Callback callback);
|
||||
Interceptor getNextInterceptor();
|
||||
}
|
||||
|
||||
private static Logger LOG = Log.getLogger(HttpOutput.class);
|
||||
|
|
|
@ -311,6 +311,21 @@ public class GzipHandler extends HandlerWrapper implements GzipFactory
|
|||
String path = context==null?baseRequest.getRequestURI():URIUtil.addPaths(baseRequest.getServletPath(),baseRequest.getPathInfo());
|
||||
LOG.debug("{} handle {} in {}",this,baseRequest,context);
|
||||
|
||||
HttpChannel channel = HttpChannel.getCurrentHttpChannel();
|
||||
HttpOutput out = channel.getResponse().getHttpOutput();
|
||||
// Are we already being gzipped?
|
||||
HttpOutput.Interceptor interceptor = out.getInterceptor();
|
||||
while (interceptor!=null)
|
||||
{
|
||||
if (interceptor instanceof GzipHttpOutputInterceptor)
|
||||
{
|
||||
LOG.debug("{} already intercepting {}",this,request);
|
||||
_handler.handle(target,baseRequest, request, response);
|
||||
return;
|
||||
}
|
||||
interceptor=interceptor.getNextInterceptor();
|
||||
}
|
||||
|
||||
// If not a supported method - no Vary because no matter what client, this URI is always excluded
|
||||
if (!_includedMethods.contains(baseRequest.getMethod()))
|
||||
{
|
||||
|
@ -366,12 +381,8 @@ public class GzipHandler extends HandlerWrapper implements GzipFactory
|
|||
request.setAttribute(ETAG,etag.replace(ETAG_GZIP,""));
|
||||
}
|
||||
|
||||
HttpChannel channel = HttpChannel.getCurrentHttpChannel();
|
||||
HttpOutput out = channel.getResponse().getHttpOutput();
|
||||
HttpOutput.Interceptor interceptor = out.getInterceptor();
|
||||
if (!(interceptor instanceof GzipHttpOutputInterceptor))
|
||||
out.setInterceptor(new GzipHttpOutputInterceptor(this,_vary,channel,interceptor));
|
||||
|
||||
// install interceptor and handle
|
||||
out.setInterceptor(new GzipHttpOutputInterceptor(this,_vary,channel,out.getInterceptor()));
|
||||
_handler.handle(target,baseRequest, request, response);
|
||||
|
||||
}
|
||||
|
|
|
@ -79,6 +79,11 @@ public class GzipHttpOutputInterceptor implements HttpOutput.Interceptor
|
|||
_bufferSize=bufferSize;
|
||||
}
|
||||
|
||||
public HttpOutput.Interceptor getNextInterceptor()
|
||||
{
|
||||
return _interceptor;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(ByteBuffer content, boolean complete, Callback callback)
|
||||
{
|
||||
|
@ -261,6 +266,10 @@ public class GzipHttpOutputInterceptor implements HttpOutput.Interceptor
|
|||
}
|
||||
}
|
||||
|
||||
public boolean mightCompress()
|
||||
{
|
||||
return _state.get()==GZState.MIGHT_COMPRESS;
|
||||
}
|
||||
private class GzipArrayCB extends IteratingNestedCallback
|
||||
{
|
||||
private final boolean _complete;
|
||||
|
|
|
@ -90,7 +90,7 @@ public abstract class AsyncTimeoutCompleteWrite extends TestDirContentServlet im
|
|||
String fileName = request.getServletPath();
|
||||
request.setAttribute("filename",fileName);
|
||||
ctx.addListener(this);
|
||||
ctx.setTimeout(200);
|
||||
ctx.setTimeout(20);
|
||||
|
||||
// Setup indication of a redispatch (which this scenario shouldn't do)
|
||||
request.setAttribute(this.getClass().getName(),ctx);
|
||||
|
|
|
@ -38,6 +38,7 @@ import org.eclipse.jetty.servlets.AsyncGzipFilter;
|
|||
import org.eclipse.jetty.servlets.GzipFilter;
|
||||
import org.eclipse.jetty.toolchain.test.TestTracker;
|
||||
import org.eclipse.jetty.toolchain.test.TestingDir;
|
||||
import org.junit.Assert;
|
||||
import org.junit.Ignore;
|
||||
import org.junit.Rule;
|
||||
import org.junit.Test;
|
||||
|
@ -155,6 +156,8 @@ public class GzipContentLengthTest
|
|||
@Test
|
||||
public void testAsyncTimeoutCompleteWrite_Default() throws Exception
|
||||
{
|
||||
if (expectCompressed && gzipFilterClass==GzipFilter.class)
|
||||
return; // Default startAsync will never work with GzipFilter, which needs wrapping
|
||||
testWithGzip(AsyncTimeoutCompleteWrite.Default.class);
|
||||
}
|
||||
|
||||
|
@ -326,9 +329,10 @@ public class GzipContentLengthTest
|
|||
* @see <a href="Eclipse Bug 450873">http://bugs.eclipse.org/450873</a>
|
||||
*/
|
||||
@Test
|
||||
@Ignore
|
||||
public void testHttpOutputWrite() throws Exception
|
||||
{
|
||||
if (gzipFilterClass == GzipFilter.class)
|
||||
return; // Can't downcaste output stream when wrapper is used
|
||||
testWithGzip(TestServletBufferTypeLengthWrite.class);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -61,7 +61,7 @@ public class TestServletBufferTypeLengthWrite extends TestDirContentServlet
|
|||
response.setHeader("ETag","W/etag-"+fileName);
|
||||
|
||||
response.setContentLength(dataBytes.length);
|
||||
|
||||
|
||||
((HttpOutput)out).write(ByteBuffer.wrap(dataBytes).asReadOnlyBuffer());
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue