web中gzip,deflate的压缩与解压

一,对发送请求进行gzip,deflate压缩

1:gzip的情况

Java代码  收藏代码
  1. Sring url = "http://localhost/save";
  2. PostMethod post = new PostMethod(url);
  3. //请求体内容
  4. String body = "sample";
  5. //用gzip方式压缩请求体并赋给request
  6. ByteArrayInputStream bis = new ByteArrayInputStream(body.getBytes());
  7. ByteArrayOutputStream bos = new ByteArrayOutputStream();
  8. GZIPOutputStream gos = new GZIPOutputStream(bos);
  9. for (int c = bis.read(); c != -1; c = bis.read()) {
  10.     gos.write(c);
  11. }
  12. gos.close();
  13. InputStreamRequestEntity entity = new InputStreamRequestEntity(new ByteArrayInputStream(bos.toByteArray()), "text/html");
  14. post.setRequestEntity(entity);
  15. post.addRequestHeader("Content-Encoding", "gzip");

 

2:deflate的情况

Java代码  收藏代码
  1. Sring url = "http://localhost/save";
  2. PostMethod post = new PostMethod(url);
  3. //请求体内容
  4. String body = "sample";
  5. //用deflate方式压缩请求体并赋给request
  6. ByteArrayInputStream bis = new ByteArrayInputStream(body.getBytes());
  7. ByteArrayOutputStream bos = new ByteArrayOutputStream();
  8. DeflaterOutputStream dos = new DeflaterOutputStream(bos);
  9. for (int c = bis.read(); c != -1; c = bis.read()) {
  10.     dos.write(c);
  11. }
  12. dos.close();
  13. InputStreamRequestEntity entity = new InputStreamRequestEntity(new ByteArrayInputStream(bos.toByteArray()), "text/html");
  14. post.setRequestEntity(entity);
  15. post.addRequestHeader("Content-Encoding", "deflate");

 

二,在服务器端使用过滤器对压缩过的请求进行解压

新建一个filter继承UserAgentFilter.java,截取req,进行包装,接着继续执行别的filters

Java代码  收藏代码
  1. @Override
  2. public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException,
  3.     ServletException {
  4.     HttpServletRequest request = (HttpServletRequest) req;
  5.     String ce = request.getHeader("Content-Encoding"); // gzip|deflate|inflate
  6.     if (ce != null) {
  7.         if (ce.indexOf("deflate") >= 0 || ce.indexOf("inflate") >= 0) {
  8.         // uncompress using inflate
  9.         request = new InflateRequestWrapper(request);
  10.         } else if (ce.indexOf("gzip") >= 0) {
  11.         // uncompress using gzip
  12.         request = new GZipRequestWrapper(request);
  13.         }
  14.     }
  15.     ......
  16.     super.doFilter(request, res, chain);
  17.     ......
  18. }

 

下面是InflateRequestWrapper的内容,GZipRequestWrapper与之类似

Java代码  收藏代码
  1. public class InflateRequestWrapper extends HttpServletRequestWrapper {
  2.     private BufferedServletInputStreamWrapper _stream;
  3.     public InflateRequestWrapper(HttpServletRequest request) throws IOException {
  4.         super(request);
  5.         _stream = new BufferedServletInputStreamWrapper(new InflaterInputStream(request.getInputStream()), request.getContentLength());
  6.     }
  7.     @Override
  8.     public BufferedServletInputStreamWrapper getInputStream() {
  9.         return _stream;
  10.     }
  11.     @Override
  12.     public int getContentLength() {
  13.         return _stream.getBytes().length;
  14.     }
  15. }

 

下面是BufferedServletInputStreamWrapper的内容

Java代码  收藏代码
  1. public class BufferedServletInputStreamWrapper extends ServletInputStream {
  2.     private static final int DEFAULT_READ_BUFFER_SIZE = 1024;
  3.     private final byte[] EMPTY_ARRAY = new byte[0];
  4.     private ByteArrayInputStream _is;
  5.     private byte[] _bytes;
  6.     /**
  7.      * takes in the actual input stream that we should be buffering
  8.      */
  9.     public BufferedServletInputStreamWrapper(InflaterInputStream stream, int length) throws IOException {
  10.         _bytes = (length == 0) ? EMPTY_ARRAY : toBytes(stream, length);
  11.         _is = new ByteArrayInputStream(_bytes);
  12.     }
  13.     @Override
  14.     public int read() throws IOException {
  15.         return _is.read();
  16.     }
  17.     @Override
  18.     public int read(byte[] buf,
  19.                     int off,
  20.                     int len) {
  21.         return _is.read(buf, off, len);
  22.     }
  23.     @Override
  24.     public int read(byte[] buf) throws IOException {
  25.         return _is.read(buf);
  26.     }
  27.     @Override
  28.     public int available() {
  29.         return _is.available();
  30.     }
  31.     /**
  32.      * resets the wrapper's stream so that it can be re-read from the stream. if we're
  33.      * using this somewhere were we expect it to be done again in the chain this should
  34.      * be called after we're through so we can reset the data.
  35.      */
  36.     public void resetWrapper() {
  37.         _is = new ByteArrayInputStream(_bytes);
  38.     }
  39.     public byte[] getBytes() {
  40.         return _bytes;
  41.     }
  42.     private byte[] toBytes(InputStream is, int bufferSize) throws IOException {
  43.         bufferSize = (bufferSize <= 0) ? DEFAULT_READ_BUFFER_SIZE : bufferSize;
  44.         ByteArrayOutputStream bos = new ByteArrayOutputStream();
  45.         byte[] buffer = new byte[bufferSize];
  46.         int read = is.read(buffer);
  47.         while (-1 != read) {
  48.             bos.write(buffer, 0, read);
  49.             read = is.read(buffer);
  50.         }
  51.         return bos.toByteArray();
  52.     }
  53. }

 

三,服务器对response进行压缩可参考jetty相关源码

 

四,java客户端对压缩过的返回值进行解压

1,gzip的情况

Java代码  收藏代码
  1. GZIPInputStream gzip = new GZIPInputStream(post.getResponseBodyAsStream());
  2. StringBuffer out = new StringBuffer();
  3. byte[] b = new byte[4096];
  4. for (int n; (n = gzip.read(b)) != -1;) {
  5.     out.append(new String(b, 0, n));
  6. }
  7. return out.toString();

 

2,deflate的情况

Java代码  收藏代码
  1. InflaterInputStream iis = new InflaterInputStream(post.getResponseBodyAsStream());
  2. contentLength = (contentLength <= 0) ? 1024 : contentLength;
  3. ByteArrayOutputStream bos = new ByteArrayOutputStream();
  4. byte[] buffer = new byte[contentLength];
  5. int read = iis.read(buffer);
  6. while (-1 != read) {
  7.     bos.write(buffer, 0, read);
  8.     read = iis.read(buffer);
  9. }
  10. byte[] _bytes = (contentLength == 0) ? EMPTY_ARRAY : bos.toByteArray();
  11. ByteArrayInputStream _is = new ByteArrayInputStream(_bytes);
  12. StringBuffer out = new StringBuffer();
  13. byte[] b = new byte[4096];
  14. for (int n; (n = _is.read(b)) != -1;) {
  15.     out.append(new String(b, 0, n));
  16. }
  17. return out.toString();
  1. da shang
    donate-alipay
               donate-weixin weixinpay

发表评论↓↓