码迷,mamicode.com
首页 > 移动开发 > 详细

HttpServletRequestWrapper、HttpServletResponseWrapper,HttpSessionWrapper用法

时间:2017-10-16 16:36:04      阅读:360      评论:0      收藏:0      [点我收藏+]

标签:架构   log   为什么   共享   private   覆盖   大致   one   utf-8   

 转载自:http://blog.csdn.net/it_man/article/details/7556903
 
 
背景:项目使用的SOA架构,使用Oracle10G SOA SUITE,在该套件中增加了一个过滤器用于解析设置的访问策略。在其中遇到了一个问题,Oracle10g无法将IP与实例编号进行绑定,于是乎从过滤器入手,尝试了HttpServletRequestWrapper、HttpServletResponseWrapper拦截设置参数的方法。得到的结果request可以对请求参数进行修改,但是这样可能会导致Oracle10g SOA Suite的正常运行,想从response中获得返回的内容,但是得到的结果是null,到目前为止该问题仍旧没有得到解决,有好办法的欢迎联系本人,谢谢。 

1)建立一个响应包装器。扩展javax.servlet.http.HttpServletResponseWrapper。

2)提供一个缓存输出的PrintWriter。重载getWriter方法,返回一个保存发送给它的所有东西的PrintWriter,并把结果存进一个可以稍后访问的字段中。

3)传递该包装器给doFilter。此调用是合法的,因为HttpServletResponseWrapper实现HttpServletResponse。

4)提取和修改输出。在调用FilterChain的doFilter方法后,原资源的输出只要利用步骤2中提供的机制就可以得到。只要对你的应用适合,就可以修改或替换它。

5)发送修改过的输出到客户机。因为原资源不再发送输出到客户机(这些输出已经存放到你的响应包装器中了),所以必须发送这些输出。这样,你的过滤器需要从原响应对象中获得PrintWriter或OutputStream,并传递修改过的输出到该流中。 (2).GZipFilter类 (3).GZipUtil类 (4).在web.xml中配置 GZipFilter


下附HttpServletRequestWrapper、HttpServletResponseWrapper用法
 1 class FilteredRequest extends HttpServletRequestWrapper  
 2     {  
 3   
 4         public FilteredRequest(ServletRequest request)  
 5         {  
 6             super((HttpServletRequest) request);  
 7         }  
 8   
 9         public String getParameter(String paramName)  
10         {  
11             String value = super.getParameter(paramName);  
12             if ("myParameter".equals(paramName))  
13             {  
14                 // 更改请求参数的值  
15                 value += "|127.0.0.1";  
16             }  
17             return value;  
18         }  
19   
20         public String[] getParameterValues(String paramName)  
21         {  
22             String values[] = super.getParameterValues(paramName);  
23             return values;  
24         }  
25     }  

 

 1 import java.io.ByteArrayOutputStream;  
 2 import java.io.IOException;  
 3 import java.io.PrintWriter;  
 4 import java.io.UnsupportedEncodingException;  
 5   
 6 import javax.servlet.ServletResponse;  
 7 import javax.servlet.http.HttpServletResponse;  
 8 import javax.servlet.http.HttpServletResponseWrapper;  
 9   
10 public class WrapperResponse extends HttpServletResponseWrapper  
11 {  
12     private MyPrintWriter tmpWriter;  
13   
14     private ByteArrayOutputStream output;  
15   
16     public WrapperResponse(ServletResponse httpServletResponse)  
17     {  
18         super((HttpServletResponse)httpServletResponse);  
19         output = new ByteArrayOutputStream();  
20         tmpWriter = new MyPrintWriter(output);  
21     }  
22   
23     public void finalize() throws Throwable  
24     {  
25         super.finalize();  
26         output.close();  
27         tmpWriter.close();  
28     }  
29   
30     public String getContent()  
31     {  
32         try  
33         {  
34             tmpWriter.flush(); //刷新该流的缓冲,详看java.io.Writer.flush()     
35             String s = tmpWriter.getByteArrayOutputStream().toString("UTF-8");  
36             //此处可根据需要进行对输出流以及Writer的重置操作     
37             //比如tmpWriter.getByteArrayOutputStream().reset()     
38             return s;  
39         } catch (UnsupportedEncodingException e)  
40         {  
41             return "UnsupportedEncoding";  
42         }  
43     }  
44   
45     //覆盖getWriter()方法,使用我们自己定义的Writer     
46     public PrintWriter getWriter() throws IOException  
47     {  
48         return tmpWriter;  
49     }  
50   
51     public void close() throws IOException  
52     {  
53         tmpWriter.close();  
54     }  
55   
56     //自定义PrintWriter,为的是把response流写到自己指定的输入流当中     
57     //而非默认的ServletOutputStream     
58     private static class MyPrintWriter extends PrintWriter  
59     {  
60         ByteArrayOutputStream myOutput; //此即为存放response输入流的对象     
61   
62         public MyPrintWriter(ByteArrayOutputStream output)  
63         {  
64             super(output);  
65             myOutput = output;  
66         }  
67   
68         public ByteArrayOutputStream getByteArrayOutputStream()  
69         {  
70             return myOutput;  
71         }  
72     }  
73 }  

 

调用处

1 FilteredRequest filterRequest = new FilteredRequest(request);  
2 WrapperResponse filterResponse = new WrapperResponse(response);  
3 filterChain.doFilter(filterRequest, filterResponse);  
4 String content = filterResponse.getContent();  
或者自己实现HttpServletResponse和HttpServletRequest接口,但这是麻烦的。
如果要管理session,或session实现共享就用HttpSessionWrapper
首先说一个无关的,但高手必须了解的。 servlet的Response的输出流在URL中保存Session ID的方法是哪一个?
A. the encodeURL method of the HttpServletRequest interface
B. the encodeURL method of the HttpServletResponse interface
C. the rewriteURL method of the HttpServletRequest interface
D. the rewriteURL method of the HttpServletResponse interface
 
答案选B.
 
学习完黎老师讲的oscache页面缓存后,它的实现原理大致如下(原理和oscache一样,但oscache做的更好,我这里只是用伪代码简单描述):
Cachefilter implements  filter{
dofilter(request, response, chain){
String urlpath = req,...;
if(Oscache.contains(urlpath)){
String content = oscache.getKey(urlpath);
response.write(content);
}else{
CacheHettpServletResponseWrapper wrapper = new CacheHettpServletResponseWrapper (respone);
chain.doFilter(reques, wrapper);
String content = wrapper.getContent();//获取服务端往客户端输出的html代码
Oscache.put(urlpath, content);
response.write(content);
}
}
}
 
public CacheHettpServletResponseWrapper extends  HettpServletResponseWrapper{
private String content;
public CacheHettpServletResponseWrapper(HttpServletResponse response){
.......
}
//重写HettpServletResponseWrapper的一个方法,这里可能不是write方法,忘记叫什么了,自己去看。后来看了下是
1 //覆盖getWriter()方法,使用我们自己定义的Writer     
2     public PrintWriter getWriter() throws IOException  

HettpServletResponseWrapper吧

public void getWriter(String Content){
this.Content = content;
}
public String getContent(){
return this.content;
}
}
 
:利用继承HettpServletResponseWrapper可以控制往客户端的输出,或在往客户端输出前取得要输出的内容。
同样希望大家会HttpServletRequestWrapper。 或者自己实现HttpServletResponse和HttpServletRequest接口,但这是麻烦的。

1)建立一个响应包装器。扩展javax.servlet.http.HttpServletResponseWrapper。

2)提供一个缓存输出的PrintWriter。重载getWriter方法,返回一个保存发送给它的所有东西的PrintWriter,并把结果存进一个可以稍后访问的字段中。

3)传递该包装器给doFilter。此调用是合法的,因为HttpServletResponseWrapper实现HttpServletResponse。

4)提取和修改输出。在调用FilterChain的doFilter方法后,原资源的输出只要利用步骤2中提供的机制就可以得到。只要对你的应用适合,就可以修改或替换它。

5)发送修改过的输出到客户机。因为原资源不再发送输出到客户机(这些输出已经存放到你的响应包装器中了),所以必须发送这些输出。这样,你的过滤器需要从原响应对象中获得PrintWriter或OutputStream,并传递修改过的输出到该流中。 (2).GZipFilter类 (3).GZipUtil类 (4).在web.xml中配置 GZipFilter

--------------------------------------------------
页面缓存
---》html--->client
二级缓存
--》action-->service层-->Jsp-->html-->client
 
:从上看出为什么页面缓存要比二级缓存要快。因为二级缓存处理流程更多,并且还要解析jsp及标签等转化成html,这是耗时的。
 

 

HttpServletRequestWrapper、HttpServletResponseWrapper,HttpSessionWrapper用法

标签:架构   log   为什么   共享   private   覆盖   大致   one   utf-8   

原文地址:http://www.cnblogs.com/cvcn/p/7677149.html

(1)
(1)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!