Merged branch 'jetty-9.3.x' into 'master'.

This commit is contained in:
Simone Bordet 2016-02-22 11:34:07 +01:00
commit c52c8304d8
2 changed files with 26 additions and 16 deletions

View File

@ -31,14 +31,17 @@ import java.util.Iterator;
import java.util.NoSuchElementException; import java.util.NoSuchElementException;
import org.eclipse.jetty.client.api.ContentProvider; import org.eclipse.jetty.client.api.ContentProvider;
import org.eclipse.jetty.io.ByteBufferPool;
import org.eclipse.jetty.util.log.Log; import org.eclipse.jetty.util.log.Log;
import org.eclipse.jetty.util.log.Logger; import org.eclipse.jetty.util.log.Logger;
/** /**
* A {@link ContentProvider} for files using JDK 7's {@code java.nio.file} APIs. * <p>A {@link ContentProvider} for files using JDK 7's {@code java.nio.file} APIs.</p>
* <p> * <p>It is possible to specify, at the constructor, a buffer size used to read
* It is possible to specify, at the constructor, a buffer size used to read content from the * content from the stream, by default 4096 bytes.
* stream, by default 4096 bytes. * If a {@link ByteBufferPool} is provided via {@link #setByteBufferPool(ByteBufferPool)},
* the buffer will be allocated from that pool, otherwise one buffer will be
* allocated and used to read the file.</p>
*/ */
public class PathContentProvider extends AbstractTypedContentProvider public class PathContentProvider extends AbstractTypedContentProvider
{ {
@ -47,6 +50,7 @@ public class PathContentProvider extends AbstractTypedContentProvider
private final Path filePath; private final Path filePath;
private final long fileSize; private final long fileSize;
private final int bufferSize; private final int bufferSize;
private ByteBufferPool bufferPool;
public PathContentProvider(Path filePath) throws IOException public PathContentProvider(Path filePath) throws IOException
{ {
@ -81,6 +85,16 @@ public class PathContentProvider extends AbstractTypedContentProvider
return fileSize; return fileSize;
} }
public ByteBufferPool getByteBufferPool()
{
return bufferPool;
}
public void setByteBufferPool(ByteBufferPool byteBufferPool)
{
this.bufferPool = byteBufferPool;
}
@Override @Override
public Iterator<ByteBuffer> iterator() public Iterator<ByteBuffer> iterator()
{ {
@ -89,7 +103,7 @@ public class PathContentProvider extends AbstractTypedContentProvider
private class PathIterator implements Iterator<ByteBuffer>, Closeable private class PathIterator implements Iterator<ByteBuffer>, Closeable
{ {
private final ByteBuffer buffer = ByteBuffer.allocateDirect(bufferSize); private ByteBuffer buffer;
private SeekableByteChannel channel; private SeekableByteChannel channel;
private long position; private long position;
@ -106,6 +120,9 @@ public class PathContentProvider extends AbstractTypedContentProvider
{ {
if (channel == null) if (channel == null)
{ {
buffer = bufferPool == null ?
ByteBuffer.allocateDirect(bufferSize) :
bufferPool.acquire(bufferSize, true);
channel = Files.newByteChannel(filePath, StandardOpenOption.READ); channel = Files.newByteChannel(filePath, StandardOpenOption.READ);
if (LOG.isDebugEnabled()) if (LOG.isDebugEnabled())
LOG.debug("Opened file {}", filePath); LOG.debug("Opened file {}", filePath);
@ -121,9 +138,6 @@ public class PathContentProvider extends AbstractTypedContentProvider
position += read; position += read;
if (!hasNext())
close();
buffer.flip(); buffer.flip();
return buffer; return buffer;
} }
@ -139,17 +153,13 @@ public class PathContentProvider extends AbstractTypedContentProvider
} }
} }
@Override
public void remove()
{
throw new UnsupportedOperationException();
}
@Override @Override
public void close() public void close()
{ {
try try
{ {
if (bufferPool != null && buffer != null)
bufferPool.release(buffer);
if (channel != null) if (channel != null)
channel.close(); channel.close();
} }

View File

@ -43,7 +43,6 @@ import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.Part; import javax.servlet.http.Part;
import org.eclipse.jetty.client.AbstractHttpClientServerTest; import org.eclipse.jetty.client.AbstractHttpClientServerTest;
import org.eclipse.jetty.client.api.ContentProvider;
import org.eclipse.jetty.client.api.ContentResponse; import org.eclipse.jetty.client.api.ContentResponse;
import org.eclipse.jetty.http.HttpFields; import org.eclipse.jetty.http.HttpFields;
import org.eclipse.jetty.http.HttpHeader; import org.eclipse.jetty.http.HttpHeader;
@ -284,7 +283,8 @@ public class MultiPartContentProviderTest extends AbstractHttpClientServerTest
}); });
MultiPartContentProvider multiPart = new MultiPartContentProvider(); MultiPartContentProvider multiPart = new MultiPartContentProvider();
ContentProvider content = new PathContentProvider(contentType, tmpPath); PathContentProvider content = new PathContentProvider(contentType, tmpPath);
content.setByteBufferPool(client.getByteBufferPool());
multiPart.addFilePart(name, tmpPath.getFileName().toString(), content, null); multiPart.addFilePart(name, tmpPath.getFileName().toString(), content, null);
multiPart.close(); multiPart.close();
ContentResponse response = client.newRequest("localhost", connector.getLocalPort()) ContentResponse response = client.newRequest("localhost", connector.getLocalPort())