HttpServletResponseWrapper取返回值

360 阅读2分钟

1.使用前提

需要在Filter过滤器doFilter方法中使用,使用示列:

@Override
public void doFilter(ServletRequest rq, ServletResponse rp, FilterChain chain){
    HttpServletRequest request=(HttpServletRequest) rq;
    HttpServletResponse response=(HttpServletResponse) rp;
    //2.使用复制响应包装过滤器的响应执行chain.doFilter
    HttpServletResponseCopier wrapper = new HttpServletResponseCopier(response);
    try {
        chain.doFilter(request, wrapper);
    } catch (Exception e) {
        //执行chain.doFilter(request, wrapper);时发生异常:
    }
    //3.(将截取的响应写出给过滤器的响应)一.截取向浏览器写入结果,二.写出响应给浏览器
    String result = wrapper.writeResponse(response);
}

优势:

1.无需操心HttpServletResponse是PrintWriter还是OutputStream方式写出结果都可以获取到值。

2.使用简单依赖即用

其他注意事项:

该jar包是我私人的包,该包只有200多k 其中只有三个类,使用maven项目的小伙伴需要解压反编译后使用。

三个类我这里展示出来也可以去下载jar包 HttpServletResponseCopier:

import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintWriter;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpServletResponseWrapper;

public class HttpServletResponseCopier extends HttpServletResponseWrapper {
	
    private ServletOutputStreamCopier streamCopier;
    private PrintWriterCopier         writerCopier;
    //true=使用PrintWriterCopier;false=使用ServletOutputStreamCopier
    private boolean                   useWriter;
    private int 					  statusCode;

    public HttpServletResponseCopier(HttpServletResponse response) throws IOException {
        super(response);
        useWriter = true;
    }
    
    /**
	 * 复制response相应流(自动判断使用PrintWriter/OutputStream)
	 * @param response	接收浏览器请求时的响应HttpServletResponse结果对象
	 * @return	response响应到浏览器内容
	 * @throws IOException
	 */
	public String writeResponse(HttpServletResponse response) throws IOException {
    	String rest="";
    	if (this.isUseWriter()) {
    		rest=new String(this.getWriterCopy());
    		PrintWriter out = response.getWriter();
    		out.write(this.getWriterCopy());
    		out.flush();
    		out.close();
    	} else {
    		rest=new String(this.getStreamCopy(),response.getCharacterEncoding());
    		OutputStream out = response.getOutputStream();
    		out.write(this.getStreamCopy());
    		out.flush();
    		out.close();
    	}
    	return rest;
    }
	
    
    @Override
    public ServletOutputStream getOutputStream() throws IOException {
        if (writerCopier != null) {
            throw new IllegalStateException("getWriter() has already been called on this response.");
        }

        if (streamCopier == null) {
            useWriter = false;
            streamCopier = new ServletOutputStreamCopier();
        }

        return streamCopier;
    }

    @Override
    public PrintWriter getWriter() throws IOException {
        if (streamCopier != null) {
            throw new IllegalStateException("getOutputStream() has already been called on this response.");
        }

        if (writerCopier == null) {
            useWriter = true;
            writerCopier = new PrintWriterCopier();
        }

        return writerCopier.getWriter();
    }

    public byte[] getBytes() {
        if (streamCopier==null && writerCopier==null) {
            return new byte[0];
        }

        return useWriter ? writerCopier.getBytes() : streamCopier.getCopy();
    }

    public byte[] getStreamCopy() {
        if (useWriter) {
            throw new IllegalStateException("already use writer, please call getWriterCopy()");
        }

        return streamCopier==null ? new byte[0] : streamCopier.getCopy();
    }

    public char[] getWriterCopy() {
        if (!useWriter) {
            throw new IllegalStateException("already use outputStream, please call getStreamCopy()");
        }

        return writerCopier==null ? new char[0] : writerCopier.getCopy();
    }

    /**
     * The default behavior of this method is to call sendError(int sc, String msg)
     * on the wrapped response object.
     */
    public void sendError(int sc, String msg) throws IOException {
        ((HttpServletResponse)getResponse()).sendError(sc, msg);
        this.statusCode = sc;
    }

    /**
     * The default behavior of this method is to call sendError(int sc)
     * on the wrapped response object.
     */
    public void sendError(int sc) throws IOException {
        ((HttpServletResponse)getResponse()).sendError(sc);
        this.statusCode = sc;
    }

    public void setStatus(int sc) {
        super.setStatus(sc);
        this.statusCode = sc;
    }

    /**
     * The default behavior of this method is to call setStatus(int sc, String sm)
     * on the wrapped response object.
     */
    public void setStatus(int sc, String sm) {
        super.setStatus(sc, sm);
        this.statusCode = sc;
    }

    public int getStatus() {
        return statusCode;
    }

    /**
     * 是否使用PrintWriterCopier写出响应结果
     * @return	true=使用PrintWriterCopier;false=使用ServletOutputStreamCopier
     */
    public boolean isUseWriter() {
        return useWriter;
    }
}

PrintWriterCopier

import java.io.CharArrayWriter;
import java.io.PrintWriter;

public class PrintWriterCopier {
    private CharArrayWriter charArrayWriter;
    private PrintWriter writer;

    public PrintWriterCopier() {
        this.charArrayWriter = new CharArrayWriter();
        this.writer = new PrintWriter(charArrayWriter);
    }

    public PrintWriter getWriter() {
        return writer;
    }

    public char[] getCopy() {
        return charArrayWriter.toCharArray();
    }

    public byte[] getBytes() {
        return charArrayWriter.toString().getBytes();
    }
}

ServletOutputStreamCopier


import java.io.ByteArrayOutputStream;
import java.io.IOException;
import javax.servlet.ServletOutputStream;
import javax.servlet.WriteListener;

/**
 * 拷贝Servlet输出
 *
 * Created by hai on 16/12/13.
 */
public class ServletOutputStreamCopier extends ServletOutputStream {
    private static final int INIT_BUFFER_SIZE = 1024;

    private ByteArrayOutputStream copy;

    public ServletOutputStreamCopier() {
        this.copy = new ByteArrayOutputStream(INIT_BUFFER_SIZE);
    }

    @Override
    public void write(int b) throws IOException {
        copy.write(b);
    }

    public byte[] getCopy() {
        return copy.toByteArray();
    }

    @Override
    public void flush() throws IOException {
        copy.flush();
    }

	@Override
	public boolean isReady() {
		// TODO Auto-generated method stub
		return false;
	}

	@Override
	public void setWriteListener(WriteListener arg0) {
		// TODO Auto-generated method stub
		
	}
}

HttpServletResponseCopier下载jar

阿里云盘:阿里云盘分享

————————————————

提取码:t6i2