缓存filter及资源池模式

 一。缓存过滤器模式
1。概念:缓存过滤器模式是通过使用servlet的filter来动态地缓存生成的页面,从而提高web层的性能和伸缩性。工作原理非常简单,当第一次请求到来时,判断是否可以缓存,可以的话就放在缓存里。当下次请求时,直接从缓存中取出,而不是再次请求。
2。一个简单实现对html页面的缓存:
None.gif package  cfexample.controller;
None.gif
None.gif
import  java.io. * ;
None.gif
import  javax.servlet. * ;
None.gif
import  javax.servlet.http. * ;
None.gif
ExpandedBlockStart.gifContractedBlock.gif
/** */ /**
InBlock.gif *用来替代HttpServletReponse的新对象,以提供缓存能力
ExpandedBlockEnd.gif 
*/

ExpandedBlockStart.gifContractedBlock.gif
public   class  CacheResponseWrapper  extends  HttpServletResponseWrapper  dot.gif {
InBlock.gif
InBlock.gif    
private CacheOutputStream outStream;
InBlock.gif    
InBlock.gif    
//替换OutputStream和PrintWriter
InBlock.gif
    private ServletOutputStream stream;
InBlock.gif    
private PrintWriter writer;
InBlock.gif    
InBlock.gif   
ExpandedSubBlockStart.gifContractedSubBlock.gif    
class CacheOutputStream extends ServletOutputStream dot.gif{
InBlock.gif 
InBlock.gif        
private ByteArrayOutputStream bos;
InBlock.gif 
ExpandedSubBlockStart.gifContractedSubBlock.gif        CacheOutputStream() 
dot.gif{
InBlock.gif            bos 
= new ByteArrayOutputStream();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif    
ExpandedSubBlockStart.gifContractedSubBlock.gif        
public void write(int param) throws IOException dot.gif{
InBlock.gif            bos.write(param);
ExpandedSubBlockEnd.gif        }

InBlock.gif        
ExpandedSubBlockStart.gifContractedSubBlock.gif        
public void write(byte[] b, int off, int len) throws IOException dot.gif{
InBlock.gif            bos.write(b, off, len);
ExpandedSubBlockEnd.gif        }

InBlock.gif        
ExpandedSubBlockStart.gifContractedSubBlock.gif        
protected byte[] getBytes() dot.gif{
InBlock.gif            
return bos.toByteArray();
ExpandedSubBlockEnd.gif        }

ExpandedSubBlockEnd.gif    }

InBlock.gif    
ExpandedSubBlockStart.gifContractedSubBlock.gif     
public CacheResponseWrapper(HttpServletResponse original) dot.gif{
InBlock.gif        
super(original);
ExpandedSubBlockEnd.gif    }

InBlock.gif    
InBlock.gif    
protected ServletOutputStream createOutputStream() 
InBlock.gif        
throws IOException
ExpandedSubBlockStart.gifContractedSubBlock.gif    
dot.gif{
InBlock.gif        outStream 
= new CacheOutputStream();
InBlock.gif        
return outStream;
ExpandedSubBlockEnd.gif    }

InBlock.gif    
InBlock.gif    
public ServletOutputStream getOutputStream()
InBlock.gif        
throws IOException 
ExpandedSubBlockStart.gifContractedSubBlock.gif    
dot.gif{
ExpandedSubBlockStart.gifContractedSubBlock.gif        
if (stream != nulldot.gif{
InBlock.gif            
return stream;
ExpandedSubBlockEnd.gif        }

InBlock.gif        
ExpandedSubBlockStart.gifContractedSubBlock.gif        
if (writer != nulldot.gif{
InBlock.gif            
throw new IOException("Writer already in use");
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        stream 
= createOutputStream();
InBlock.gif        
return stream;
ExpandedSubBlockEnd.gif    }

InBlock.gif    
ExpandedSubBlockStart.gifContractedSubBlock.gif     
public PrintWriter getWriter() throws IOException dot.gif{
ExpandedSubBlockStart.gifContractedSubBlock.gif        
if (writer != nulldot.gif{
InBlock.gif            
return writer;
ExpandedSubBlockEnd.gif        }

InBlock.gif        
ExpandedSubBlockStart.gifContractedSubBlock.gif        
if (stream != nulldot.gif{
InBlock.gif            
throw new IOException("OutputStream already in use");
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        writer 
= new PrintWriter(new OutputStreamWriter(createOutputStream()));
InBlock.gif        
return writer;
ExpandedSubBlockEnd.gif    }

ExpandedSubBlockStart.gifContractedSubBlock.gif    
protected byte[] getBytes() throws IOException dot.gif{
ExpandedSubBlockStart.gifContractedSubBlock.gif        
if (outStream != nulldot.gif{
InBlock.gif            
return outStream.getBytes();
ExpandedSubBlockEnd.gif        }

InBlock.gif        
InBlock.gif        
return null;
ExpandedSubBlockEnd.gif    }

ExpandedBlockEnd.gif}

None.gif
None.gif
// CacheFilter.java 过滤器:
None.gif
package  cfexample.controller;
None.gif
None.gif
import  java.io. * ;
None.gif
import  java.net. * ;
None.gif
import  java.util. * ;
None.gif
import  java.text. * ;
None.gif
import  javax.servlet. * ;
None.gif
import  javax.servlet.http. * ;
None.gif
None.gif
import  javax.servlet.Filter;
None.gif
import  javax.servlet.FilterChain;
None.gif
import  javax.servlet.FilterConfig;
None.gif
import  javax.servlet.ServletContext;
None.gif
import  javax.servlet.ServletException;
None.gif
import  javax.servlet.ServletRequest;
None.gif
import  javax.servlet.ServletResponse;
ExpandedBlockStart.gifContractedBlock.gif
public   class  CacheFilter  implements  Filter  dot.gif {
InBlock.gif
InBlock.gif    
private FilterConfig filterConfig = null;
InBlock.gif    
InBlock.gif    
//缓存池
InBlock.gif
    private HashMap cache;
InBlock.gif    
ExpandedSubBlockStart.gifContractedSubBlock.gif    
public CacheFilter() dot.gif{
ExpandedSubBlockEnd.gif    }

InBlock.gif    
public void doFilter(ServletRequest request, 
InBlock.gif                         ServletResponse response,
InBlock.gif                         FilterChain chain)
InBlock.gif        
throws IOException, ServletException
ExpandedSubBlockStart.gifContractedSubBlock.gif    
dot.gif{
InBlock.gif        HttpServletRequest req 
= (HttpServletRequest) request;
InBlock.gif        HttpServletResponse res 
= (HttpServletResponse) response;
InBlock.gif       
InBlock.gif        
//缓存子中的键URI+查询字符串
InBlock.gif
        String key = req.getRequestURI() + "?" + req.getQueryString();
InBlock.gif        
InBlock.gif        
//只缓存get请求的内容
ExpandedSubBlockStart.gifContractedSubBlock.gif
        if (req.getMethod().equalsIgnoreCase("get"&& isCacheable(key)) dot.gif{
InBlock.gif            
byte[] data = (byte[]) cache.get(key);
InBlock.gif            
InBlock.gif           
//池中没有,生成并存入
ExpandedSubBlockStart.gifContractedSubBlock.gif
            if (data == nulldot.gif{
InBlock.gif                CacheResponseWrapper crw 
= new CacheResponseWrapper(res);
InBlock.gif                chain.doFilter(request, crw);
InBlock.gif                data 
= crw.getBytes();
InBlock.gif                cache.put(key, data);
ExpandedSubBlockEnd.gif            }
 
InBlock.gif            
InBlock.gif            
// 如果有的话,直接得到返回
ExpandedSubBlockStart.gifContractedSubBlock.gif
            if (data != nulldot.gif{
InBlock.gif                res.setContentType(
"text/html");
InBlock.gif                res.setContentLength(data.length);
InBlock.gif                
ExpandedSubBlockStart.gifContractedSubBlock.gif                
try dot.gif{
InBlock.gif                    OutputStream os 
= res.getOutputStream();
InBlock.gif                    os.write(data);
InBlock.gif                    os.flush();
InBlock.gif                    os.close();
ExpandedSubBlockStart.gifContractedSubBlock.gif                }
 catch(Exception ex) dot.gif{
InBlock.gif                    ex.printStackTrace();
ExpandedSubBlockEnd.gif                }

ExpandedSubBlockEnd.gif            }

ExpandedSubBlockStart.gifContractedSubBlock.gif        }
 else dot.gif{
InBlock.gif            
// generate the data normally if it was not cacheable
InBlock.gif
            chain.doFilter(request, response);
ExpandedSubBlockEnd.gif        }

ExpandedSubBlockEnd.gif    }

InBlock.gif    
InBlock.gif    
//判断是否可以缓存,考虑一个配置文件配置哪些可以缓存,此处省去
ExpandedSubBlockStart.gifContractedSubBlock.gif
    private boolean isCacheable(String key) dot.gif{
InBlock.gif        
return true;
ExpandedSubBlockEnd.gif    }

InBlock.gif    
InBlock.gif    
ExpandedSubBlockStart.gifContractedSubBlock.gif    
public void init(FilterConfig filterConfig) dot.gif{
InBlock.gif        
this.filterConfig = filterConfig;
InBlock.gif        
InBlock.gif        cache 
= new HashMap();
ExpandedSubBlockEnd.gif    }

ExpandedSubBlockStart.gifContractedSubBlock.gif    
public void destroy() dot.gif{
InBlock.gif        cache.clear();
InBlock.gif        
InBlock.gif        cache 
= null;
InBlock.gif        filterConfig 
= null;
ExpandedSubBlockEnd.gif    }

ExpandedBlockEnd.gif}

None.gif


3.实际应用例子:oscache是很好的解决web层缓存的方案!!准备认真读读它的源代码。

二。资源池模式:
1。概念:一个资源池就是一组预先生成的对象,它们可以被出借以便节省多次chuang创建它们所花费的时间。典型的如:EJB池(Service Locator一般都有一个ejb的home接口池),数据库连接池。

2。优点:A。提高了应用的可伸缩性,使资源的创建和开销不至于失控。B,产生了一个统一的有效微调点,通过运行时修改池参数来影响应用的性能等因素。

3。简单实现:
(1)首先一个创建对象的工厂:
None.gif package  pool;
None.gif
ExpandedBlockStart.gifContractedBlock.gif
public   interface  ResourceFactory  dot.gif {
InBlock.gif    
public Object createResource();
InBlock.gif    
InBlock.gif    
//验证返回的资源,并提供还原
InBlock.gif
    public boolean validateResource(Object o);
ExpandedBlockEnd.gif}


(2)资源池:
None.gif
OutliningIndic
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值