OSCache簡述


官網: http://www.opensymphony.com/oscache [緩存產品有:EHCahce、OSCache、JbossCache(分布式緩存)]
例子:
http://www.java.net/downloads/oscache/OSCache/2.4.1/oscache-example.war

OSCache是什么

OSCache是OpenSymphony這個開源項目眾多Projects中的一個。他是一個高效的J2EE緩存框架,能夠很好的解決動態網站速度的問題。下面來看下OSCache解決了動態網站的哪些令人郁悶的問題。
   1.緩存動態內容:其實我們的動態網頁上一般只有一部分是動態的(表頭,表尾一般是不變的),如果我們緩存整個網頁顯然不成,因為有部分是隨着請求有可能變的。OSCache提供的方式是允許我們只緩存一部分網頁。
   2.緩存2進制內容:產生的圖片和PDF文件在服務器加載的時候非常的耗時。OSCache解決這個問題是通過一個Servlet2.3的緩存過濾功能,然后能夠緩存任意的URI(比如一個完整的頁面或者是一個產生的圖片/PDF文件)
   3.容錯:有這種情況或許我們會遇到,就是當一個動態的網頁出現錯誤。即便我們的頁面有95%都加載完畢,但就是由於這個錯誤,整個頁面就會返回錯誤的提示或頁面。OSCache允許我們提供出現錯誤時的緩存內容,如果出現就適時的提示出來了。
   除了上面的這些Servlet的特征外,OSCache完全可以充當任何一個java程序的緩存方案。OSCache 的一般特征如下:
   1.緩存任意對象:可以不受限制的緩存JSP的一部分或是Http請求,任何的Java對象都可以被緩存。
   2.全面的API:通過API可以完完全全的控制OSCache的任何特性。
   3.持久緩存:我們可以把認為重要的數據緩存到硬盤上。
   4.支持集群:集群緩存數據能被單個的進行參數配置,不需要修改代碼(如果需要集群緩存,把jgroups.jar放入classpath)
   5.緩存記錄的過期:你可以有最大限度的控制緩存對象的過期,包括可插入式的刷新策略(如果默認性能不需要時)。

OSCache運行環境

如果用到OSCache Tag Library的話,需要Servlet2.3和JSP1.2的支持。如果是直接用OSCache API的話那么就不需要Servlet容器的支持。
目前可以正常運行的Web容器:
1.OrionServer(版本1.4.0和更高)
2.JRun(3.0或更好)
3.WebLogic(8.1或以上)
4.Websphere(5.0或以上)
5.Resin(1.2.3或以上)
6.TomCat(4.0或以上)
7.iPlanet(6.0或以上)
用到緩存過濾需要Servlet2.3支持.目前知道的可以個工作在OrionServer,WebLogic,Tomcat上.OSCache需要Java的版本至少是java 1.4

OSCache緩存配置

從src\webapp\WEB-INF\classes或etc目錄取得oscache.properties文件,放在CLASSPATH下src根目錄,oscache.properties包含了對OSCache運行特征值的設置信息

配置項

含義

可選值

缺省值

cache.memory

是否進行內存緩存

true、false

true

cache.capacity

內存緩存容納的最大對象數

整數

不限制(指定負數也相當於不限制),也就是緩存的對象從不被清除

cache.algorithm

缺省的運算規則。要指定運算規則,就必須指定有效的cache.capacity值(正整數)。規則是一些類,在包com.opensymphony.oscache.base.algorithm下

LRUCache(最近使用)、FIFOCache(先進先出)、UnlimitedCache(不限制)

不限制cache.capacity時為UnlimitedCache,If you specify a size but not an algorithm, the cache algorithm used will be LRUCache

cache.blocking

當緩存中的某條數據更新時(比如與數據庫不同步,存在不新鮮的數據),對客戶請求返回更新前的數據。這樣就提供了更好的性能。

true、false

false

cache.unlimited.disk

硬盤緩存是否有限制。缺省為cache.capacity指定的值

true、false

false

cache.persistence.class

做持久化操作的類名。這個類必須實現PersistenceListener接口,從而將緩存數據持久化到文件、數據庫、LDAP。OSCache給出一個基於文件系統的實現,並且使用對象的toString()方法生成要持久化數據的文件名。HashDiskPersistenceListener和 DiskPersistenceListener要求必須同時設置cache.path屬性。

com.opensymphony.oscache.plugins.

diskpersistence.DiskPersistenceListener 

 

cache.path

硬盤持久化時存放文件的目錄。如果目錄不存在OSCache會自動創建。

Windows系統: c:\\myapp\\cache

其它:/opt/myapp/cache

 

cache.persistence.overflow.only*

是否只有當指定的內存緩存已經滿時才進行持久化。推薦使用true,flase是為向后兼容。

true
false

false

cache.event.listeners

一系列用逗號分割的類,這些類必須實現CacheEntryEventListener或(和)CacheMapAccessEventListener接口,CacheEntryEventListener監聽緩存的add/update/flush/remove事件,CacheMapAccessEventListener監聽緩存的access事件,從而可以跟蹤並統計緩存的執行效率。JavaDoc API for further details.

 

 

cache.key

指定在application或session范圍里緩存的對象的key,這個key被ServletCacheAdministrator(由此自定義的tags)使用。

 

__oscache_cache

cache.use.host.domain.in.key

If your server is configured with multiple hosts, you may wish to add host name information to automatically generated cache keys. If so, set this property to true

true
  false

false

cache.cluster.multicast.ip

見集群的相關說明

 

 

cache.cluster.properties

見集群的相關說明

 

 

緩存方式

   1.緩存對象(內存緩存,磁盤緩存)
將一個對象以key-value的形式放入緩存中,主要通過GeneralCacheAdministrator類來實現。寫了個單例,其實是不必要的

public class OSCacheHelper<T> extends GeneralCacheAdministrator {
    private static final long serialVersionUID = 1L;
    private static Logger logger = Logger.getLogger(OSCacheHelper.class);
    private static Object lock = new Object();
    private static OSCacheHelper instance;
    private OSCacheHelper() {
    }
    public static OSCacheHelper getInstance() {
        if (instance == null) {
            synchronized (lock) {
                if (instance == null) {
                    instance = new OSCacheHelper();
                }
            }
        }
        return instance;
    }

    /**
     * put on Object in a cache
     */
    public void putToCache(String key, T data) {
        try {
            this.putInCache(key, data);
            logger.info(key + " put in Cache success");
        } catch (Exception e) {
            logger.info(key + " put in Cache faile"+e.getMessage());
        }
    }

    /**
     * get on Object from the Cache
     */
    public T getFromCache(String key, int time) {
        try {
            return (T) this.getFromCache(key, time);
        } catch (Exception e) {
            logger.info(key + " is not found in Cache");
        }
        return null;
    }

    /**
     * remove an Object in a cache
     */
    public void removeEntry(String key) {
        this.removeEntry(key);
    }

    /**
     * flushes a single cache entry
     */
    public void flushEntry(String key) {
        this.flushEntry(key);
    }

    /**
     * flush the entire cache immediately
     */
    public void flushAll() {
        this.flushAll();
    }

    /*
     * cancel a pending cache update
     */
    public void cancelUpdate(String key) {
        this.cancelUpdate(key);
    }

    /**
     * 刪除指定日期所有被緩存的對象
     */
    public void flushAll(Date date) {
        this.flushAll(date);
    }
}

SpringMVC下測試

@Controller
public class OscaheController extends BaseCache {
    private static final long serialVersionUID = 1L;
    protected static Logger logger = Logger.getLogger(OscaheController.class);

    // 文件緩存讀取
    @RequestMapping(value = "putCache.shtml")
    public String putCache() {
        Map<String, List<User>> ms_map = new HashMap<String, List<User>>();
        List<User> list = new ArrayList<User>();
        for (int j = 0; j < 100; j++) {
            for (int i = 0; i < 500; i++) {
                User user = new User();
                user.setId(i);
                user.setEmail(2538XXXXX + i + "@163.com");
                user.setNickname("Irving");
                user.setUsername("sd" + new Date().toLocaleString());
                user.setAdddate(new Date());
                list.add(user);
            }
            ms_map.put(String.valueOf(list.get(0).getId()), list);
        }
        //this.putToCache("CACHE_NEW_MS_PRICE_OBJ", ms_map);
        OSCacheHelper.getInstance().putToCache("CACHE_NEW_MS_PRICE_OBJ", ms_map);
        return "putCache";
    }

    @RequestMapping(value = "loadCache.shtml")
    public void loadCache() {
        Map<String, List<User>> ms_map = new HashMap<String, List<User>>();
        ms_map = (Map<String, List<User>>) this.getFromCache("CACHE_NEW_MS_PRICE_OBJ", 31536000);
        for (Object o : ms_map.keySet()) {
            List<User> user = ms_map.get(o);
            for (User u : user) {
                logger.info("ID:" + u.getId() + " Email:" + u.getEmail() + " UserName:" + u.getUsername());
            }
        }
    }
}

2.局部頁面緩存(導入標簽庫)

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@ page language="java" import="java.text.*" %>  
<%@ taglib uri="http://www.opensymphony.com/oscache" prefix="cache"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <title>頁面局部緩存</title>
  </head>
  <body>
    <%
        SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    %>  
    <div>  
        <cache:cache key="cacheDate" scope="session" time="10">   
            <h2>使用緩存,在10秒內不進行更新</h2>  
            <div><%
                  String cacheTime = sf.format(new Date());
                      out.println(cacheTime);
              %>  
            </div>  
        </cache:cache>  
    </div>  
    <hr>  
    <div>  
        <h2>不使用緩存</h2>  
        <div><%
              String nowTime = sf.format(new Date());
              out.println(nowTime);
          %></div>  
    </div> 
  </body>
</html>

3.整個頁面緩存

<filter>   
      <filter-name>CacheFilter</filter-name>   
        <filter-class>com.opensymphony.oscache.web.filter.CacheFilter</filter-class>    
        <init-param>    
         <param-name>time</param-name>   
         <param-value>500</param-value>   
      </init-param>    
      <init-param>     
         <param-name>scope</param-name>    
         <param-value>session</param-value>   
      </init-param>    
</filter>     
<filter-mapping>     
<filter-name>CacheFilter</filter-name>   
<!-對所有shtml頁面內容進行緩存-->     
<url-pattern>*.shtml</url-pattern>    
</filter-mapping>

4.分布式緩存(沒有研究)

小結

1、清除緩存:

<!-- refresh為true將會導致緩存的內容過期而被清除,簡單地說,該屬性為true用於清除緩存 -->
<!-- <oscache:flush scope="application"/>清除application范圍內的所有緩存;
<oscache:flush scope="session" key="huhui"/>       #清除session范圍內的key為huhui的緩存
<oscache:flush scope="application" group="hu"/>    #清除application范圍內組名為hu內的所有緩存 -->
<%@ page language="java" pageEncoding="UTF-8"%>
<%@taglib uri="http://www.opensymphony.com/oscache" prefix="oscache" %>
<oscache:flush scope="applocation"/>               #緩存已清除

2、局部緩存:

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@ taglib uri="http://www.opensymphony.com/oscache" prefix="oscache" %>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <title>My JSP 'index.jsp' starting page</title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
  </head>
  <body><!-- 這是局部緩存 -->
  <oscache:cache key="huhui" scope="session" time="15" refresh="${param.refresh }">
  <!-- 是使用Map對象來存儲緩存的,默認的key是uri路徑,如:/oscache/index.jsp,也可以指定它的key -->
  <!-- 緩存默認存放在application范圍,緩存時間默認為3600秒,即1小時 -->
    <div><%=new Date() %></div>
  </oscache:cache>
  當前時間:<%=new Date() %>
  </body>
</html>

3、全局緩存:web.xml

<!-- 設置頁面的全局緩存 -->
  <filter>
<filter-name>CacheFilter</filter-name>
<filter-class>com.opensymphony.oscache.web.filter.CacheFilter</filter-class>
<init-param>
<param-name>time</param-name>
<param-value>7200</param-value>
</init-param>
<init-param>
    <param-name>scope</param-name>
    <param-value>application</param-value>
</init-param>
   </filter>
   <filter-mapping>
<filter-name>CacheFilter</filter-name>
<url-pattern>/hotel/list.shtml</url-pattern>
</filter-mapping>

4、內存緩存/硬盤緩存推薦使用內存緩存,比硬盤緩存要快

oscache.properties
#指定是否使用內存緩存,默認值為true,即使用內存緩存
cache.memory=true
#指定緩存的容量,默認的容量是無限的
cache.capacity=10000
#如果要使用硬盤緩存,可以這樣設置:
cache.memory=false
#指定緩存保存的路徑
cache.path=/opt/springmvc/cache
#用於設置持久化的類
cache.persistence.class=com.opensymphony.oscache.plugins.diskpersistence.DiskPersistenceListener

Refer:
http://blog.chinaunix.net/uid-122937-id-142910.html
http://blog.csdn.net/zhifeng172/article/details/7608682
http://blog.csdn.net/orclight/article/category/1331444


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM