<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    我的Blog我做主^_^

    走向一條通往JAVA的不歸路...

      BlogJava :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理 ::
      64 隨筆 :: 68 文章 :: 77 評論 :: 0 Trackbacks

    OSCache是當前運用最廣的緩存方案,JBoss,Hibernate,Spring等都對其有支持,
    下面簡單介紹一下OSCache的配置和使用過程。

    1.安裝過程
    http://www.opensymphony.com/oscache/download.html 下載合適的OSCache版本,
    我下載的是oscache-2.0.2-full版本。
    解壓縮下載的文件到指定目錄

    從解壓縮目錄取得oscache.jar 文件放到 /WEB-INF/lib 或相應類庫目錄 目錄中,
    jar文件名可能含有版本號和該版本的發布日期信息等,如oscache-2.0.2-22Jan04.jar

    如果你的jdk版本為1.3.x,建議在lib中加入Apache Common Lib 的commons-collections.jar包。
    如jdk是1.4以上則不必

    從src或etc目錄取得oscache.properties 文件,放入src根目錄或發布環境的/WEB-INF/classes 目錄
    如你需要建立磁盤緩存,須修改oscache.properties 中的cache.path信息 (去掉前面的#注釋)。
    win類路徑類似為c:\\app\\cache
    unix類路徑類似為/opt/myapp/cache

    拷貝OSCache標簽庫文件oscache.tld到/WEB-INF/classes目錄。

    現在你的應用目錄類似如下:
    $WEB_APPLICATION\WEB-INF\lib\oscache.jar
    $WEB_APPLICATION\WEB-INF\classes\oscache.properties
    $WEB_APPLICATION\WEB-INF\classes\oscache.tld


    將下列代碼加入web.xml文件中
    <taglib>
    <taglib-uri>oscache</taglib-uri>
    <taglib-location>/WEB-INF/classes/oscache.tld</taglib-location>
    </taglib>

    為了便于調試日志輸出,須加入commons-logging.jar和log4j-1.2.8.jar到當前類庫路徑中

    在src目錄加入下面兩個日志輸出配置文件:
    log4j.properties 文件內容為:
    log4j.rootLogger=DEBUG,stdout,file

    log4j.appender.stdout=org.apache.log4j.ConsoleAppender
    log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
    log4j.appender.stdout.layout.ConversionPattern=[start]%d{yyyy/MM/dd/ HH:mm:ss}[DATE]%n%p[PRIORITY]%n%x[NDC]%n%t[THREAD] n%c[CATEGORY]%n%m[MESSAGE]%n%n

    ?

    log4j.appender.file=org.apache.log4j.RollingFileAppender
    log4j.appender.file.File=oscache.log
    log4j.appender.file.MaxFileSize=100KB
    log4j.appender.file.MaxBackupIndex=5
    log4j.appender.file.layout=org.apache.log4j.PatternLayout
    log4j.appender.file.layout.ConversionPattern=[start]%d{yyyy/MM/dd/ HH:mm:ss}[DATE]%n%p[PRIORITY]%n%x[NDC]%n%t[THREAD] n%c[CATEGORY]%n%m[MESSAGE]%n%n


    log4j.logger.org.apache.commons=ERROR
    log4j.logger.com.opensymphony.oscache.base=INFO


    commons-logging.properties 文件內容為

    org.apache.commons.logging.Log=org.apache.commons.logging.impl.Log4JCategoryLog

    2.oscache.properties 文件配置向導

    cache.memory
    值為true 或 false ,默認為在內存中作緩存,
    如設置為false,那cache只能緩存到數據庫或硬盤中,那cache還有什么意義:)

    cache.capacity
    緩存元素個數

    cache.persistence.class
    持久化緩存類,如此類打開,則必須設置cache.path信息

    cache.cluster 相關
    為集群設置信息。

    cache.cluster.multicast.ip為廣播IP地址
    cache.cluster.properties為集群屬性


    3.OSCache的基本用法

    cache1.jsp 內容如下

    <%@ page import="java.util.*" %>
    <%@ taglib uri="oscache" prefix="cache" %>

    <html>
    <body>

    沒有緩存的日期: <%= new Date() %><p>
    <!--自動刷新-->
    <cache:cache time="30">
    每30秒刷新緩存一次的日期: <%= new Date() %>
    </cache:cache>
    <!--手動刷新-->
    <cache:cache key="testcache">
    手動刷新緩存的日期: <%= new Date() %> <p>
    </cache:cache>
    <a href="/cache2.jsp">手動刷新</a>

    </body>
    </html>

    cache2.jsp 執行手動刷新頁面如下
    <%@ taglib uri="oscache" prefix="cache" %>

    <html>
    <body>

    緩存已刷新...<p>

    <cache:flush key="testcache" scope="application"/>

    <a href="/cache1.jsp">返回</a>

    </body>
    </html>

    OSCache庫提供的flush標記能夠刷新緩沖內容。我們可以把下面的代碼加入到處理用戶動作且可能影響這一區域的頁面之中:

    <cache:flush key="testcache" scope="application"/>

    當用戶下次訪問它時,testcache緩沖塊將被刷新


    你也可以通過下面語句定義Cache的有效范圍,如不定義scope,scope默認為Applcation
    <cache:cache time="30" scope="session">
    ...
    </cache:cache>

    4. 緩存過濾器 CacheFilter

    package com.lvke.company.common;

    import com.opensymphony.oscache.base.Cache;
    import com.opensymphony.oscache.base.EntryRefreshPolicy;
    import com.opensymphony.oscache.base.NeedsRefreshException;
    import com.opensymphony.oscache.web.ServletCacheAdministrator;

    import org.apache.commons.logging.Log;
    import org.apache.commons.logging.LogFactory;

    import java.io.IOException;

    import javax.servlet.*;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import javax.servlet.jsp.PageContext;
    import com.opensymphony.oscache.web.filter.CacheHttpServletResponseWrapper;
    import com.opensymphony.oscache.web.filter.ICacheGroupsProvider;
    import com.opensymphony.oscache.web.filter.ICacheKeyProvider;
    import com.opensymphony.oscache.web.filter.ExpiresRefreshPolicy;
    import com.opensymphony.oscache.web.filter.ResponseContent;

    public class CacheFilter implements Filter, ICacheKeyProvider, ICacheGroupsProvider {
    ??? // Header
    ??? public static final String HEADER_LAST_MODIFIED = "Last-Modified";
    ??? public static final String HEADER_CONTENT_TYPE = "Content-Type";
    ??? public static final String HEADER_CONTENT_ENCODING = "Content-Encoding";
    ??? public static final String HEADER_EXPIRES = "Expires";
    ??? public static final String HEADER_IF_MODIFIED_SINCE = "If-Modified-Since";
    ??? public static final String HEADER_CACHE_CONTROL = "Cache-Control";
    ??? public static final String HEADER_ACCEPT_ENCODING = "Accept-Encoding";

    ??? // Fragment parameter
    ??? public static final int FRAGMENT_AUTODETECT = -1;
    ??? public static final int FRAGMENT_NO = 0;
    ??? public static final int FRAGMENT_YES = 1;

    ??? // No cache parameter
    ??? public static final int NOCACHE_OFF = 0;
    ??? public static final int NOCACHE_SESSION_ID_IN_URL = 1;

    ??? // Last Modified parameter
    ??? public static final long LAST_MODIFIED_OFF = 0;
    ??? public static final long LAST_MODIFIED_ON = 1;
    ??? public static final long LAST_MODIFIED_INITIAL = -1;

    ??? // Expires parameter
    ??? public static final long EXPIRES_OFF = 0;
    ??? public static final long EXPIRES_ON = 1;
    ??? public static final long EXPIRES_TIME = -1;

    ??? // Cache Control
    ??? public static final long MAX_AGE_NO_INIT = Long.MIN_VALUE;
    ??? public static final long MAX_AGE_TIME = Long.MAX_VALUE;

    ??? // request attribute to avoid reentrance
    ??? private final static String REQUEST_FILTERED = "__oscache_filtered";

    ??? // the policy for the expires header
    ??? private EntryRefreshPolicy expiresRefreshPolicy;

    ??? // the logger
    ??? private final Log log = LogFactory.getLog(this.getClass());

    ??? // filter variables
    ??? private FilterConfig config;
    ??? private ServletCacheAdministrator admin = null;
    ??? private int cacheScope = PageContext.APPLICATION_SCOPE; // filter scope - default is APPLICATION
    ??? private int fragment = FRAGMENT_AUTODETECT; // defines if this filter handles fragments of a page - default is auto detect
    ??? private int time = 60 * 60; // time before cache should be refreshed - default one hour (in seconds)
    ??? private String cron = null; // A cron expression that determines when this cached content will expire - default is null
    ??? private int nocache = NOCACHE_OFF; // defines special no cache option for the requests - default is off
    ??? private long lastModified = LAST_MODIFIED_INITIAL; // defines if the last-modified-header will be sent - default is intial setting
    ??? private long expires = EXPIRES_ON; // defines if the expires-header will be sent - default is on
    ??? private long cacheControlMaxAge = -60; // defines which max-age in Cache-Control to be set - default is 60 seconds for max-age
    ??? private ICacheKeyProvider cacheKeyProvider = this; // the provider of the cache key - default is the CacheFilter itselfs
    ??? private ICacheGroupsProvider cacheGroupsProvider = this; // the provider of the cache groups - default is the CacheFilter itselfs

    ??? /**
    ???? * Filter clean-up
    ???? */
    ??? public void destroy() {
    ??????? //Not much to do...
    ??? }

    ??? public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
    ??????? if (log.isInfoEnabled()) {
    ??????????? log.info("<cache>: filter in scope " + cacheScope);
    ??????? }

    ??????? // avoid reentrance (CACHE-128) and check if request is cacheable
    ??????? if (isFilteredBefore(request) || !isCacheable(request)) {
    ??????????? chain.doFilter(request, response);
    ??????????? return;
    ??????? }
    ??????? request.setAttribute(REQUEST_FILTERED, Boolean.TRUE);

    ??????? HttpServletRequest httpRequest = (HttpServletRequest) request;

    ??????? // checks if the response will be a fragment of a page
    ??????? boolean fragmentRequest = isFragment(httpRequest);

    ??????? // avoid useless session creation for application scope pages (CACHE-129)
    ??????? Cache cache;
    ??????? if (cacheScope == PageContext.SESSION_SCOPE) {
    ??????????? cache = admin.getSessionScopeCache(httpRequest.getSession(true));
    ??????? } else {
    ??????????? cache = admin.getAppScopeCache(config.getServletContext());
    ??????? }

    ??????? // generate the cache entry key
    ??????? String key = cacheKeyProvider.createCacheKey(httpRequest, admin, cache);

    ??????? try {
    ??????????? ResponseContent respContent = (ResponseContent) cache.getFromCache(key, time, cron);

    ??????????? if (log.isInfoEnabled()) {
    ??????????????? log.info("<cache>: Using cached entry for " + key);
    ??????????? }

    ??????????? boolean acceptsGZip = false;
    ??????????? if ((!fragmentRequest) && (lastModified != LAST_MODIFIED_OFF)) {
    ??????????????? long clientLastModified = httpRequest.getDateHeader(HEADER_IF_MODIFIED_SINCE); // will return -1 if no header...

    ??????????????? // only reply with SC_NOT_MODIFIED
    ??????????????? // if the client has already the newest page and the response isn't a fragment in a page
    ??????????????? if ((clientLastModified != -1) && (clientLastModified >= respContent.getLastModified())) {
    ??????????????????? ((HttpServletResponse) response).setStatus(HttpServletResponse.SC_NOT_MODIFIED);
    ??????????????????? return;
    ??????????????? }

    ??????????????? acceptsGZip = respContent.isContentGZiped() && acceptsGZipEncoding(httpRequest);
    ??????????? }

    ??????????? respContent.writeTo(response, fragmentRequest, acceptsGZip);
    ??????????? // acceptsGZip is used for performance reasons above; use the following line for CACHE-49
    ??????????? // respContent.writeTo(response, fragmentRequest, acceptsGZipEncoding(httpRequest));
    ??????? } catch (NeedsRefreshException nre) {
    ??????????? boolean updateSucceeded = false;

    ??????????? try {
    ??????????????? if (log.isInfoEnabled()) {
    ??????????????????? log.info("<cache>: New cache entry, cache stale or cache scope flushed for " + key);
    ??????????????? }

    ??????????????? CacheHttpServletResponseWrapper cacheResponse = new CacheHttpServletResponseWrapper((HttpServletResponse) response, fragmentRequest, time * 1000L, lastModified, expires, cacheControlMaxAge);
    ??????????????? chain.doFilter(request, cacheResponse);
    ??????????????? cacheResponse.flushBuffer();

    ??????????????? // Only cache if the response is cacheable
    ??????????????? if (isCacheable(cacheResponse)) {
    ??????????????????? // get the cache groups of the content
    ??????????????????? String[] groups = cacheGroupsProvider.createCacheGroups(httpRequest, admin, cache);
    ??????????????????? // Store as the cache content the result of the response
    ??????????????????? cache.putInCache(key, cacheResponse.getContent(), groups, expiresRefreshPolicy, null);
    ??????????????????? updateSucceeded = true;
    ??????????????? }
    ??????????? } finally {
    ??????????????? if (!updateSucceeded) {
    ??????????????????? cache.cancelUpdate(key);
    ??????????????? }
    ??????????? }
    ??????? }
    ??? }


    ??? public void init(FilterConfig filterConfig) {
    ??????? //Get whatever settings we want...
    ??????? config = filterConfig;
    ??????? admin = ServletCacheAdministrator.getInstance(config.getServletContext());

    ??????? // filter parameter time
    ??????? try {
    ??????????? time = Integer.parseInt(config.getInitParameter("time"));
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'time', defaulting to one hour.");
    ??????? }

    ??????? // setting the refresh period for this cache filter
    ??????? expiresRefreshPolicy = new ExpiresRefreshPolicy(time);

    ??????? // filter parameter scope
    ??????? try {
    ??????????? String scopeString = config.getInitParameter("scope");

    ??????????? if (scopeString.equals("session")) {
    ??????????????? cacheScope = PageContext.SESSION_SCOPE;
    ??????????? } else if (scopeString.equals("application")) {
    ??????????????? cacheScope = PageContext.APPLICATION_SCOPE;
    ??????????? } else if (scopeString.equals("request")) {
    ??????????????? cacheScope = PageContext.REQUEST_SCOPE;
    ??????????? } else if (scopeString.equals("page")) {
    ??????????????? cacheScope = PageContext.PAGE_SCOPE;
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'scope', defaulting to 'application'.");
    ??????? }

    ??????? // filter parameter cron
    ??????? cron = config.getInitParameter("cron");

    ??????? // filter parameter fragment
    ??????? try {
    ??????????? String fragmentString = config.getInitParameter("fragment");

    ??????????? if (fragmentString.equals("no")) {
    ??????????????? fragment = FRAGMENT_NO;
    ??????????? } else if (fragmentString.equals("yes")) {
    ??????????????? fragment = FRAGMENT_YES;
    ??????????? } else if (fragmentString.equalsIgnoreCase("auto")) {
    ??????????????? fragment = FRAGMENT_AUTODETECT;
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'fragment', defaulting to 'auto detect'.");
    ??????? }

    ??????? // filter parameter nocache
    ??????? try {
    ??????????? String nocacheString = config.getInitParameter("nocache");

    ??????????? if (nocacheString.equals("off")) {
    ??????????????? nocache = NOCACHE_OFF;
    ??????????? } else if (nocacheString.equalsIgnoreCase("sessionIdInURL")) {
    ??????????????? nocache = NOCACHE_SESSION_ID_IN_URL;
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'nocache', defaulting to 'off'.");
    ??????? }

    ??????? // filter parameter last modified
    ??????? try {
    ??????????? String lastModifiedString = config.getInitParameter("lastModified");

    ??????????? if (lastModifiedString.equals("off")) {
    ??????????????? lastModified = LAST_MODIFIED_OFF;
    ??????????? } else if (lastModifiedString.equals("on")) {
    ??????????????? lastModified = LAST_MODIFIED_ON;
    ??????????? } else if (lastModifiedString.equalsIgnoreCase("initial")) {
    ??????????????? lastModified = LAST_MODIFIED_INITIAL;
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'lastModified', defaulting to 'initial'.");
    ??????? }

    ??????? // filter parameter expires
    ??????? try {
    ??????????? String expiresString = config.getInitParameter("expires");

    ??????????? if (expiresString.equals("off")) {
    ??????????????? expires = EXPIRES_OFF;
    ??????????? } else if (expiresString.equals("on")) {
    ??????????????? expires = EXPIRES_ON;
    ??????????? } else if (expiresString.equalsIgnoreCase("time")) {
    ??????????????? expires = EXPIRES_TIME;
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'expires', defaulting to 'on'.");
    ??????? }

    ??????? // filter parameter Cache-Control
    ??????? try {
    ??????????? String cacheControlMaxAgeString = config.getInitParameter("max-age");

    ??????????? if (cacheControlMaxAgeString.equals("no init")) {
    ??????????????????? cacheControlMaxAge = MAX_AGE_NO_INIT;
    ??????????? } else if (cacheControlMaxAgeString.equals("time")) {
    ??????????????????? cacheControlMaxAge = MAX_AGE_TIME;
    ??????????? } else {
    ??????????????????? cacheControlMaxAge = Long.parseLong(cacheControlMaxAgeString);
    ??????????????????? if (cacheControlMaxAge >= 0) {
    ??????????????????????????? // declare the cache control as a constant
    ??????????????????????????? cacheControlMaxAge = - cacheControlMaxAge;
    ??????????????????? } else {
    ??????????????????? log.warn("Init parameter 'max-age' must be at least a positive integer, defaulting to 'time'. ");
    ??????????????????????? cacheControlMaxAge = 60;
    ??????????????????? }
    ??????????? }
    ??????? } catch (Exception e) {
    ??????????? log.info("Could not get init parameter 'max-age', defaulting to 'time'.");
    ??????? }

    ??????? // filter parameter ICacheKeyProvider
    ??????? ICacheKeyProvider cacheKeyProvider = (ICacheKeyProvider)instantiateFromInitParam("ICacheKeyProvider", ICacheKeyProvider.class, this.getClass().getName());
    ??????? if (cacheKeyProvider != null) {
    ??????????? this.cacheKeyProvider = cacheKeyProvider;
    ??????? }

    ??????? // filter parameter ICacheGroupsProvider
    ??????? ICacheGroupsProvider cacheGroupsProvider = (ICacheGroupsProvider)instantiateFromInitParam("ICacheGroupsProvider", ICacheGroupsProvider.class, this.getClass().getName());
    ??????? if (cacheGroupsProvider != null) {
    ??????????? this.cacheGroupsProvider = cacheGroupsProvider;
    ??????? }

    ??????? // filter parameter EntryRefreshPolicy
    ??????? EntryRefreshPolicy expiresRefreshPolicy = (EntryRefreshPolicy)instantiateFromInitParam("EntryRefreshPolicy", EntryRefreshPolicy.class, this.expiresRefreshPolicy.getClass().getName());
    ??????? if (expiresRefreshPolicy != null) {
    ??????????? this.expiresRefreshPolicy = expiresRefreshPolicy;
    ??????? }
    ??? }

    ??? private Object instantiateFromInitParam(String classInitParam, Class interfaceClass, String defaultClassName) {
    ??????????????? String className = config.getInitParameter(classInitParam);
    ??????????????? if (className == null) {
    ??????????????????????? log.info("Could not get init parameter '" + classInitParam + "', defaulting to " + defaultClassName + ".");
    ??????????????????????? return null;
    ??????????????? } else {
    ??????????????????????? try {
    ??????????????????????????????? Class clazz = Class.forName(className);
    ??????????????????????????????? if (!interfaceClass.isAssignableFrom(clazz)) {
    ??????????????????????????????????????? log.error("Specified class '" + className + "' does not implement" + interfaceClass.getName() + ". Using default " + defaultClassName + ".");
    ??????????????????????????????????????? return null;
    ??????????????????????????????? } else {
    ??????????????????????????????????????? return clazz.newInstance();
    ??????????????????????????????? }
    ??????????????????????? } catch (ClassNotFoundException e) {
    ??????????????????????????????? log.error("Class '" + className + "' not found. Defaulting to " + defaultClassName + ".", e);
    ??????????????????????? } catch (InstantiationException e) {
    ??????????????????????????????? log.error("Class '" + className + "' could not be instantiated because it is not a concrete class. Using default class " + defaultClassName + ".", e);
    ??????????????????????? } catch (IllegalAccessException e) {
    ??????????????????????????????? log.error("Class '"+ className+ "' could not be instantiated because it is not public. Using default class " + defaultClassName + ".", e);
    ??????????????????????? }
    ??????????????????????? return null;
    ??????????????? }
    ??????? }


    ??? public String createCacheKey(HttpServletRequest httpRequest, ServletCacheAdministrator scAdmin, Cache cache) {
    ??????? return scAdmin.generateEntryKey(null, httpRequest, cacheScope);
    ??? }

    ??? public String[] createCacheGroups(HttpServletRequest httpRequest, ServletCacheAdministrator scAdmin, Cache cache) {
    ??????? return null;
    ??? }


    ??? protected boolean isFragment(HttpServletRequest request) {
    ??????? if (fragment == FRAGMENT_AUTODETECT) {
    ??????????? return request.getAttribute("javax.servlet.include.request_uri") != null;
    ??????? } else {
    ??????????? return (fragment == FRAGMENT_NO) ? false : true;
    ??????? }
    ??? }

    ??? protected boolean isFilteredBefore(ServletRequest request) {
    ??????? return request.getAttribute(REQUEST_FILTERED) != null;
    ??? }

    ??? protected boolean isCacheable(ServletRequest request) {
    ??????? // TODO implement CACHE-137 and CACHE-141 here
    ??????? boolean cachable = request instanceof HttpServletRequest;

    ??????? if (cachable) {
    ??????????? HttpServletRequest requestHttp = (HttpServletRequest) request;
    ??????????? if (nocache == NOCACHE_SESSION_ID_IN_URL) { // don't cache requests if session id is in the URL
    ??????????????? cachable = !requestHttp.isRequestedSessionIdFromURL();
    ??????????? }
    ??????? }

    ??????? if (log.isDebugEnabled()) {
    ??????????? log.debug("<cache>: the request " + ((cachable) ? "is" : "is not") + " cachable.");
    ??????? }

    ??????? return cachable;
    ??? }

    ??? protected boolean isCacheable(CacheHttpServletResponseWrapper cacheResponse) {
    ??????? // TODO implement CACHE-137 and CACHE-141 here
    ??????? // Only cache if the response was 200
    ??????? boolean cachable = cacheResponse.getStatus() == HttpServletResponse.SC_OK;

    ??????? if (log.isDebugEnabled()) {
    ??????????? log.debug("<cache>: the response " + ((cachable) ? "is" : "is not") + " cachable.");
    ??????? }

    ??????? return cachable;
    ??? }


    ??? protected boolean acceptsGZipEncoding(HttpServletRequest request) {
    ??????? String acceptEncoding = request.getHeader(HEADER_ACCEPT_ENCODING);
    ??????? return? (acceptEncoding != null) && (acceptEncoding.indexOf("gzip") != -1);
    ??? }

    }


    你可以在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>60</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>
    <url-pattern>*.jsp</url-pattern>
    </filter-mapping>
    上面定義將緩存所有.jsp頁面,緩存刷新時間為60秒,緩存作用域為Session

    ?

    注意,CacheFilter只捕獲Http頭為200的頁面請求,即只對無錯誤請求作緩存,
    而不對其他請求(如500,404,400)作緩存處理

    OSCache - Tags http://www.opensymphony.com/oscache/wiki/JSP%20Tags.html
    ??
    ??注:本文引自
    http://www.zhanglihai.com/
    ????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????? 13:11:20 12-22-2006



    posted on 2006-12-22 13:16 java_蟈蟈 閱讀(878) 評論(0)  編輯  收藏 所屬分類: OPEN SOURCE
    主站蜘蛛池模板: 成人无遮挡裸免费视频在线观看| 免费观看91视频| 毛片免费观看网站| 国产亚洲精品VA片在线播放| 国产成人免费在线| 亚洲综合精品成人| 日韩中文字幕在线免费观看 | 亚洲精品资源在线| 1000部拍拍拍18勿入免费视频下载| 亚洲Av无码专区国产乱码DVD| 在线播放免费人成毛片乱码| 亚洲国产另类久久久精品| 国产成人精品无码免费看| 久久亚洲AV无码精品色午夜 | 国产亚洲av片在线观看16女人| 99在线免费观看| 亚洲国产人成网站在线电影动漫| 91久久精品国产免费一区| 久久精品国产亚洲av麻豆图片 | 亚洲美女视频免费| 成人性生交大片免费看无遮挡 | 午夜亚洲WWW湿好爽| 亚洲AV网站在线观看| 久久九九久精品国产免费直播| 无码的免费不卡毛片视频| 中文字幕中韩乱码亚洲大片| 精品国产免费一区二区三区香蕉| 亚洲一区二区三区四区在线观看| 国产在线jyzzjyzz免费麻豆| 看Aⅴ免费毛片手机播放| 亚洲香蕉成人AV网站在线观看 | 鲁丝片一区二区三区免费| 亚洲成人免费网址| 亚洲成aⅴ人片久青草影院| av永久免费网站在线观看| 亚洲国产视频久久| 国产亚洲一区区二区在线| 国产妇乱子伦视频免费| 一级毛片在线播放免费| 亚洲日产2021三区在线 | 亚洲综合成人婷婷五月网址|