成功捷徑,貴在堅持
          人為善,福雖未至禍已遠(yuǎn)離; 人為惡,禍雖未至福已遠(yuǎn)離
          <2007年3月>
          25262728123
          45678910
          11121314151617
          18192021222324
          25262728293031
          1234567

          常用鏈接

          留言簿(14)

          隨筆分類(83)

          隨筆檔案(76)

          文章分類(5)

          文章檔案(8)

          收藏夾

          最新評論

          我想把一個基于數(shù)據(jù)庫的WEB應(yīng)用程序加上緩存,以提高性能,開源的java緩存系統(tǒng)不少,先拿JCS( Java Caching System)試試。

          關(guān)于JCS的介紹,小紅帽的文章已寫得非常清楚了,附后。


          先到http://jakarta.apache.org/jcs/Downloads.html
          下載jcs-1.2.6.jar,找了半天也沒有找到它的源碼和API文檔,不知為什么?
          在這個站點有: Using JCS: Some basics for the web ,不錯,就用它練習(xí)。

          一、創(chuàng)建值對象
          假設(shè)有一BOOK,它在數(shù)據(jù)庫中的表為:
          Table BOOK
          ??BOOK_ID_PK
          ??TITLE
          ??AUTHOR
          ??ISBN
          ??PRICE
          ??PUBLISH_DATE

          創(chuàng)建值對象如下:

          package com.genericbookstore.data;
          import java.io.Serializable;
          import java.util.Date;
          public class BookVObj implements Serializable
          {
          public int bookId = 0;
          public String title;
          public String author;
          public String ISBN;
          public String price;
          public Date publishDate;
          public BookVObj()
          {
          }
          }
          二、創(chuàng)建緩存管理器
          應(yīng)用中對book數(shù)據(jù)的訪問都通過緩存管理器。
          package com.genericbookstore.data;
          import org.apache.jcs.JCS;
          // in case we want to set some special behavior
          import org.apache.jcs.engine.behavior.IElementAttributes;
          public class BookVObjManager
          {
          private static BookVObjManager instance;
          private static int checkedOut = 0;
          public static JCS bookCache;
          private BookVObjManager()//構(gòu)造函數(shù)
          {
          try
          {
          bookCache = JCS.getInstance("bookCache");
          }
          catch (Exception e)
          {
          // Handle cache region initialization failure
          }
          // Do other initialization that may be necessary, such as getting
          // references to any data access classes we may need to populate
          // value objects later
          }
          /**
          * Singleton access point to the manager.
          */
          public static BookVObjManager getInstance()
          {
          synchronized (BookVObjManager.class)
          {
          if (instance == null)
          {
          instance = new BookVObjManager();
          }
          }
          synchronized (instance)
          {
          instance.checkedOut++;
          }
          return instance;
          }
          /**
          * Retrieves a BookVObj. Default to look in the cache.
          */
          public BookVObj getBookVObj(int id)
          {
          return getBookVObj(id, true);
          }
          /**
          * Retrieves a BookVObj. Second argument decides whether to look
          * in the cache. Returns a new value object if one can't be
          * loaded from the database. Database cache synchronization is
          * handled by removing cache elements upon modification.
          */
          public BookVObj getBookVObj(int id, boolean fromCache)
          {
          BookVObj vObj = null;
          // First, if requested, attempt to load from cache
          if (fromCache)
          {
          vObj = (BookVObj) bookCache.get("BookVObj" + id);
          }
          // Either fromCache was false or the object was not found, so
          // call loadBookVObj to create it
          if (vObj == null)
          {
          vObj = loadBookVObj(id);
          }
          return vObj;
          }
          /**
          * Creates a BookVObj based on the id of the BOOK table. Data
          * access could be direct JDBC, some or mapping tool, or an EJB.
          */
          public BookVObj loadBookVObj(int id)
          {
          BookVObj vObj = new BookVObj();
          vObj.bookId = id;
          try
          {
          boolean found = false;
          // load the data and set the rest of the fields
          // set found to true if it was found
          found = true;
          // cache the value object if found
          if (found)
          {
          // could use the defaults like this
          // bookCache.put( "BookVObj" + id, vObj );
          // or specify special characteristics
          // put to cache
          bookCache.put("BookVObj" + id, vObj);
          }
          }
          catch (Exception e)
          {
          // Handle failure putting object to cache
          }
          return vObj;
          }
          /**
          * Stores BookVObj's in database. Clears old items and caches
          * new.
          */
          public void storeBookVObj(BookVObj vObj)
          {
          try
          {
          // since any cached data is no longer valid, we should
          // remove the item from the cache if it an update.
          if (vObj.bookId != 0)
          {
          bookCache.remove("BookVObj" + vObj.bookId);
          }
          // put the new object in the cache
          bookCache.put("BookVObj" + vObj.bookId, vObj);
          }
          catch (Exception e)
          {
          // Handle failure removing object or putting object to cache.
          }
          }
          }

          三、配置文件cache.ccf,它定義你配置何種類型的緩存、緩存的大小、過期時間等。

          #WEB-INF/classes/cache.ccf(以下內(nèi)容不要換行)
          jcs.default=
          jcs.default.cacheattributes=org.apache.jcs.engine.CompositeCacheAttributes
          jcs.default.cacheattributes.MaxObjects=1000
          jcs.default.cacheattributes.MemoryCacheName=org.apache.jcs.engine.memory.lru.LRUMemoryCache

          jcs.default.cacheattributes.UseMemoryShrinker=true
          jcs.default.cacheattributes.MaxMemoryIdleTimeSeconds=3600
          jcs.default.cacheattributes.ShrinkerIntervalSeconds=60
          jcs.default.cacheattributes.MaxSpoolPerRun=500
          jcs.default.elementattributes=org.apache.jcs.engine.ElementAttributes
          jcs.default.elementattributes.IsEternal=false

          四、測試的JSP文件
          <%@page import="com.genericbookstore.data.*,java.util.*" %>

          <%

          BookVObjManager cache = BookVObjManager.getInstance();


          BookVObj bv1=cache.getBookVObj(8,true);

          out.println(bv1.bookId);
          %>

          五、測試:http://127.0.0.1:8080/jcs/testjcs.jsp

          所有源文件請下載。

          附: JCS(Java Caching System)簡介以及相關(guān)文檔

          作者:小紅帽

          概述
          JCS是Jakarta的項目Turbine的子項目。它是一個復(fù)合式的緩沖工具。可以將對象緩沖到內(nèi)存、硬盤。具有緩沖對象時間過期設(shè)定。還可以通過JCS構(gòu)建具有緩沖的分布式構(gòu)架,以實現(xiàn)高性能的應(yīng)用。
          對于一些需要頻繁訪問而每訪問一次都非常消耗資源的對象,可以臨時存放在緩沖區(qū)中,這樣可以提高服務(wù)的性能。而JCS正是一個很好的緩沖工具。緩沖工具對于讀操作遠(yuǎn)遠(yuǎn)多于寫操作的應(yīng)用性能提高非常顯著。
          JCS的詳細(xì)說明在 http://jakarta.apache.org/turbine/jcs/

          JCS的特性
          JCS除了簡單的將對象緩沖在內(nèi)存中以外,還具有幾個特性,以適應(yīng)企業(yè)級緩沖系統(tǒng)的需要。這些特性包括時間過期、索引式硬盤緩沖、并行式的分布緩沖等。
          內(nèi)存緩沖
          JCS現(xiàn)在支持兩種內(nèi)存緩沖算法LRU和MRU。通常都是使用LRU算法。
          org.apache.stratum.jcs.engine.memory.lru.LRUMemoryCache
          使用內(nèi)存緩沖區(qū)需要定義緩沖區(qū)大小,當(dāng)超過緩沖區(qū)限制時,會將緩沖內(nèi)容拋棄掉。如果有配硬盤緩沖,則將擠出來的緩沖內(nèi)容寫入硬盤緩沖區(qū)。

          時間過期
          JCS對于緩沖的對象,可以設(shè)定緩沖過期時間,一個對象在緩沖區(qū)中停留的時間超過這個時間,就會被認(rèn)為是“不新鮮”而被放棄。

          索引式硬盤緩沖
          一方面,為了避免緩沖區(qū)過大,撐爆虛擬機的內(nèi)存,另一方面又希望能夠緩沖更多的對象,JCS可以將超出緩沖區(qū)大小的對象緩存到硬盤上。配置上也比較方便, 只需要指定緩沖臨時文件的存放目錄位置。硬盤緩沖將緩沖對象的內(nèi)容寫到文件上,但是將訪問索引保存在內(nèi)存中,因此也能夠達(dá)到盡可能高的訪問效率。

          并行式的分布緩沖(Lateral)
          通常,將對象緩沖在內(nèi)存中,一方面提高了應(yīng)用的性能,而另一方面卻使得應(yīng)用不可以分布式發(fā)布。因為假設(shè)一個應(yīng)用配置在兩臺服務(wù)器上并行運行,而兩臺服務(wù)器 單獨緩沖,則很容易導(dǎo)致兩個緩沖區(qū)內(nèi)容出現(xiàn)版本上的不一致而出錯。一個機器上修改了數(shù)據(jù),這個動作會影響到本地內(nèi)存緩沖區(qū)和數(shù)據(jù)庫服務(wù)器,但是卻不會通知 到另一臺服務(wù)器,導(dǎo)致另一臺上緩沖的數(shù)據(jù)實際上已經(jīng)無效了。
          并行式的分布緩沖就是解決這個問題。可以通過配置,將幾臺服務(wù)器配成一個緩沖組,組內(nèi)每臺服務(wù)器上有數(shù)據(jù)更新,會橫向?qū)⒏碌膬?nèi)容通過TCP/IP協(xié)議傳 輸?shù)狡渌?wù)器的緩沖層,這樣就可以保證不會出現(xiàn)上述情況。這個的缺點是如果組內(nèi)的并行的服務(wù)器數(shù)量增大后,組內(nèi)的數(shù)據(jù)傳輸量將會迅速上升。這種方案適合 并行服務(wù)器的數(shù)量比較少的情況。

          Client/Server式的緩沖(Remote)
          客戶/服務(wù)端式的緩沖集群。這種方式支持一個主服務(wù)器和最高達(dá)到256個客戶端。客戶端的緩沖層會嘗試連接主服務(wù)器,如果連接成功,就會在主服務(wù)器上注冊。每個客戶端有數(shù)據(jù)更新,就會通知到主服務(wù)器,主服務(wù)器會將更新通知到除消息來源的客戶端以外的所有的客戶端。
          每個客戶端可以配置超過一個服務(wù)器,第一個服務(wù)器是主服務(wù)器,如果與第一個服務(wù)器連接失敗,客戶端會嘗試與備用的服務(wù)器連接,如果連接成功,就會通過備用 服務(wù)器與其他客戶端對話,同時會定期繼續(xù)嘗試與主服務(wù)器取得連接。如果備用服務(wù)器也連接失敗,就會按照配置順序嘗試與下一個備用服務(wù)器連接。
          這種方式下,更新通知是一種輕量級的,一個機器上的數(shù)據(jù)更新,不會把整個數(shù)據(jù)傳輸出去,而只是通知一個ID,當(dāng)遠(yuǎn)程的其他機器收到更新通知后,就會把對應(yīng)ID的緩沖對象從本地的內(nèi)存緩沖區(qū)中移除,以保證不會在緩沖區(qū)內(nèi)出現(xiàn)錯誤數(shù)據(jù)。
          這種構(gòu)造需要分別配置客戶端和服務(wù)器,配置比較麻煩。

          配置方法
          JCS的好處之一,就是應(yīng)用在開發(fā)的時候,可以不用去構(gòu)思底層的緩沖配置構(gòu)架。同一個應(yīng)用,只需要修改配置,就可以改變緩沖構(gòu)架,不需要修改應(yīng)用的源代 碼。配置方法也比較簡單,就是修改配置文件cache.ccf。這個文件放置在WEB-INF/classes目錄下。配置格式類似log4j的配置文件 格式。下面介紹一下使用各種緩沖結(jié)構(gòu)的配置方法。

          內(nèi)存緩沖
          #WEB-INF/classes/cache.ccf(以下內(nèi)容不要換行)
          jcs.default=
          jcs.default.cacheattributes=org.apache.jcs.engine.CompositeCacheAttributes
          jcs.default.cacheattributes.MaxObjects=1000
          jcs.default.cacheattributes.MemoryCacheName=org.apache.jcs.engine.memory.lru.LRUMemoryCache
          上面配置了默認(rèn)緩沖屬性。一個應(yīng)用中,由于對象類型的不同,可能會使用多個緩沖區(qū),每個緩沖區(qū)都會有一個名字,如果在配置文件中沒有指明特定的緩沖區(qū)的屬 性,所有的緩沖區(qū)都會根據(jù)默認(rèn)屬性來構(gòu)建。上面的內(nèi)容,指明緩沖區(qū)的大小為存放1000個對象,內(nèi)存緩沖器使用LRUMemoryCache對象。可選的 還有MRUMemoryCache,應(yīng)該可以自定義新的內(nèi)存緩沖區(qū)。1000個緩沖對象這個容量,是指每個緩沖區(qū)都緩沖1000個,而不是指所有緩沖區(qū)總 容量。以上配置,就可以讓應(yīng)用運行起來。

          時間過期
          如果需要引入時間過期機制,則需要加上
          jcs.default.cacheattributes.cacheattributes.UseMemoryShrinker=true
          jcs.default.cacheattributes.cacheattributes.MaxMemoryIdleTimeSeconds=3600
          jcs.default.cacheattributes.cacheattributes.ShrinkerIntervalSeconds=60
          這里指明對象超過3600秒則過期,每隔60秒檢查一次。


          索引式硬盤緩沖
          索引式硬盤緩沖是輔助緩沖的一種,使用時需要做以下事情
          #定義一個硬盤緩沖區(qū)產(chǎn)生器(Factory),取名為DC
          jcs.auxiliary.DC=org.apache.stratum.jcs.auxiliary.disk.indexed.IndexedDiskCacheFactory
          jcs.auxiliary.DC.attributes=org.apache.stratum.jcs.auxiliary.disk.indexed.IndexedDiskCacheAttributes
          jcs.auxiliary.DC.attributes.DiskPath=g:/dev/jakarta-turbine-stratum/raf
          #這里其實就是指明了緩沖文件存放到那里去。
          然后,做以下修改
          jcs.default=DC
          這樣,所有未特別指定屬性的緩沖區(qū)都會自己使用一個硬盤緩沖區(qū),緩沖文件會以緩沖區(qū)的名字來命名。存放在指定的目錄下。


          橫向式的并行緩沖
          并行式的配置如下
          jcs.auxiliary.LTCP=org.apache.jcs.auxiliary.lateral.LateralCacheFactory
          jcs.auxiliary.LTCP.attributes=org.apache.jcs.auxiliary.lateral.LateralCacheAttributes
          jcs.auxiliary.LTCP.attributes.TransmissionTypeName=TCP
          jcs.auxiliary.LTCP.attributes.TcpServers=192.168.10.129:1121,192.168.10.222:1121
          jcs.auxiliary.LTCP.attributes.TcpListenerPort=1121
          jcs.auxiliary.LTCP.attributes.PutOnlyMode=false
          這里的配置是在41,129,221三臺機器上實現(xiàn)并行緩沖的。
          大家都在1121端口上監(jiān)聽,同時與另外兩臺機器連接。如果連接失敗,就會等待一個時間后再連接一次,直到連接成功為止。三臺機器中任意一臺的緩沖區(qū)發(fā)生更新,比如put和remove動作,就會把更新傳遞給另外兩臺。


          單獨指明某個緩沖區(qū)的屬性
          如果,針對某個緩沖區(qū),比如叫做TestCache1,需要單獨配置屬性,可以如下配置。
          jcs.region.testCache1=DC,LTCP
          jcs.region.testCache1.cacheattributes=org.apache.stratum.jcs.engine.CompositeCacheAttributes
          jcs.region.testCache1.cacheattributes.MaxObjects=1000
          jcs.region.testCache1.cacheattributes.MemoryCacheName=org.apache.stratum.jcs.engine.memory.lru.LRUMemoryCache
          jcs.region.testCache1.cacheattributes.UseMemoryShrinker=true
          jcs.region.testCache1.cacheattributes.MaxMemoryIdleTimeSeconds=3600
          jcs.region.testCache1.cacheattributes.ShrinkerIntervalSeconds=60

          system.GroupIdCache
          這個概念我也不是很清楚。不過JCS文檔中指出配置以下內(nèi)容會比較好。
          jcs.system.groupIdCache=DC
          jcs.system.groupIdCache.cacheattributes=org.apache.stratum.jcs.engine.CompositeCacheAttributes
          jcs.system.groupIdCache.cacheattributes.MaxObjects=10000

          jcs.system.groupIdCache.cacheattributes.MemoryCacheName=org.apache.stratum.jcs.engine.memory.lru.LRUMemoryCache
          這可能是JCS自己的組管理體系上的緩沖區(qū)。


          Client/Server式的緩沖(Remote)
          這種構(gòu)架需要單獨配置客戶端和服務(wù)端,如果要研究,可以查看 http://jakarta.apache.org/turbine/jcs/RemoteAuxCache.html

          posted on 2007-03-17 09:14 選寶網(wǎng)an9 閱讀(293) 評論(0)  編輯  收藏

          只有注冊用戶登錄后才能發(fā)表評論。


          網(wǎng)站導(dǎo)航:
          博客園   IT新聞   Chat2DB   C++博客   博問  
           
          主站蜘蛛池模板: 安泽县| 舟曲县| 夏邑县| 全南县| 潮州市| 黄冈市| 眉山市| 上虞市| 若尔盖县| 开封县| 甘德县| 鸡西市| 长垣县| 贵定县| 东平县| 开封县| 大厂| 青河县| 湛江市| 黑龙江省| 定兴县| 远安县| 德保县| 招远市| 吉隆县| 象州县| 台北县| 古丈县| 尼玛县| 大名县| 南溪县| 屏东市| 赤水市| 鸡东县| 方正县| 大名县| 沙田区| 抚州市| 无锡市| 丰原市| 抚顺市|