java HttpServletRequestWrapper,setReadListener / isFinished / isReady 的示例实现?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/29208456/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
HttpServletRequestWrapper, example implementation for setReadListener / isFinished / isReady?
提问by Marco
I am trying to adapt a HttpServletRequestWrapper (see How to read InputStream multiple times) to be able te read the HTTP Post body after consuming it in a filter. Now I run into a challenge on how to implement the ServletInputStream. As of spec 3.1 there are new methods that have to be implemented.
我正在尝试调整 HttpServletRequestWrapper(请参阅如何多次读取 InputStream),以便在过滤器中使用它后能够读取 HTTP Post 正文。现在我遇到了一个关于如何实现 ServletInputStream 的挑战。从规范 3.1 开始,必须实现一些新方法。
- isFinished
- isReady
- setReadListener
- 已完成
- 准备好了
- 设置读取监听器
I am looking for examples or some code on how these methods can be implemented. Any hints?
我正在寻找有关如何实现这些方法的示例或一些代码。任何提示?
回答by Marco
Example implementation:
示例实现:
import com.google.common.primitives.Bytes;
import javax.servlet.ReadListener;
import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Arrays;
public class AuthenticationRequestWrapper extends HttpServletRequestWrapper {
// tag::variables[]
private byte[] requestBody = new byte[0];
private boolean bufferFilled = false;
// end::variables[]
/**
- Constructs a request object wrapping the given request.
*
- @param request The request to wrap
- @throws IllegalArgumentException if the request is null
*/
public AuthenticationRequestWrapper(HttpServletRequest request) {
super(request);
}
// tag::getRequestBody[]
public byte[] getRequestBody() throws IOException {
if (bufferFilled) {
return Arrays.copyOf(requestBody, requestBody.length);
}
InputStream inputStream = super.getInputStream();
byte[] buffer = new byte[102400]; // 100kb buffer
int bytesRead;
while ((bytesRead = inputStream.read(buffer)) != -1) {
requestBody = Bytes.concat(this.requestBody, Arrays.copyOfRange(buffer, 0, bytesRead)); // <1>
}
bufferFilled = true;
return requestBody;
}
// end::getRequestBody[]
// tag::getInputStream[]
@Override
public ServletInputStream getInputStream() throws IOException {
return new CustomServletInputStream(getRequestBody()); // <1>
}
// end::getInputStream[]
private static class CustomServletInputStream extends ServletInputStream {
private ByteArrayInputStream buffer;
public CustomServletInputStream(byte[] contents) {
this.buffer = new ByteArrayInputStream(contents);
}
@Override
public int read() throws IOException {
return buffer.read();
}
@Override
public boolean isFinished() {
return buffer.available() == 0;
}
@Override
public boolean isReady() {
return true;
}
@Override
public void setReadListener(ReadListener listener) {
throw new RuntimeException("Not implemented");
}
}
}
回答by Giovanni
you can check MockHttpServletRequestin the spring framework
您可以在 spring 框架中检查MockHttpServletRequest
The source code could be found here
源代码可以在这里找到
Since Spring is open source with Apache2 license you can start from the code and build your own version.
由于 Spring 是开源的 Apache2 许可证,您可以从代码开始并构建您自己的版本。