总的思路是,利用HttpServletResponseWrapper封装HttpServletResponse,使HttpServletResponse采用我们自己定义的输入流(OutputStream)。这样,我们就可以通过这个OutputStream得到目标jsp页面内容。
这里有两个关键点。1、怎样用当前HttpServletRequest访问目标jsp而不跳转;2、怎样构建一个OutputStream,且让HttpServletResponse获得的jsp内容输入到这个OutputStream。如果解决了这两个问题,那一切好办了。
看代码:
代码1:在不跳转下访问目标jsp。就是利用RequestDispatcher.include(ServletRequest
request, ServletResponse
response)。该方法把RequestDispatcher指向的目标页面写到response中。
public static String getJspOutput(String jsppath,
HttpServletRequest request, HttpServletResponse response)
throws Exception
{
WrapperResponse wrapperResponse = new
WrapperResponse(response);
request.getRequestDispatcher(jsppath).include(request,
wrapperResponse);
return wrapperResponse.getContent();
}
此处一个自定义类WrapperResponse封装了HttpServletResponse,具体请看一下代码。
代码2:HttpServletResponse的封装类,继承自HttpServletResponseWrapper。其核心是构建一个OutputStream,且让HttpServletResponse获得的jsp内容输入到这个OutputStream。
package com.bobrow.framework.util;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.UnsupportedEncodingException;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpServletResponseWrapper;
public class WrapperResponse extends HttpServletResponseWrapper
{
private MyPrintWriter
tmpWriter;
private ByteArrayOutputStream
output;
public
WrapperResponse(HttpServletResponse httpServletResponse) {
super(httpServletResponse);
output = new ByteArrayOutputStream();
tmpWriter = new MyPrintWriter(output);
}
public void finalize() throws
Throwable {
super.finalize();
output.close();
tmpWriter.close();
}
public String getContent()
{
try {
tmpWriter.flush(); //刷新该流的缓冲,详看java.io.Writer.flush()
String s =
tmpWriter.getByteArrayOutputStream().toString("UTF-8");
//此处可根据需要进行对输出流以及Writer的重置操作
//比如tmpWriter.getByteArrayOutputStream().reset()
return s;
} catch (UnsupportedEncodingException e) {
return "UnsupportedEncoding";
}
}
//覆盖getWriter()方法,使用我们自己定义的Writer
public PrintWriter getWriter()
throws IOException {
return tmpWriter;
}
public void close() throws
IOException {
tmpWriter.close();
}
//自定义PrintWriter,为的是把response流写到自己指定的输入流当中
//而非默认的ServletOutputStream
private static class
MyPrintWriter extends PrintWriter {
ByteArrayOutputStream myOutput; //此即为存放response输入流的对象
public MyPrintWriter(ByteArrayOutputStream output) {
super(output);
myOutput = output;
}
public ByteArrayOutputStream getByteArrayOutputStream() {
return myOutput;
}
}
}