[翻譯]javax.cache: Java快取新標準
這篇文章將帶你 探索Java快取的新標準:javax.cache。
它是如何進入Java生態系統的?
這個標準是通過JSR107開發的。JSR107被包含在Java EE 7 中,由JSR342開發。Java EE 7將在2012年末完成。但是javax.cache將會同時作用於Java SE 6或更高版本,Java EE 6和Spring等其他流行環境。
JSR107還處於草案狀態。我們目前還處於0.3版本的API和參考實現。這篇文章的例子作用於這個版本。
實現
有專家團或者對實現規範感興趣的供應商如下:
Terracotta – Ehcache
Oracle – Coherence
JBoss – Infinispan
IBM – ExtemeScale
SpringSource – Gemfire
GridGain
TMax
Google App Engine Java
Terracotta將會為Ehcache釋出一個實現最終草案的javax.cache模組,然後根據javax.cache標準的最終版做出更新。
特性
從設計的角度看,基礎概念是一個裝載和控制一組快取(譯註:也可能是Cache物件)的CacheManager。基礎的API可以被看做是一種類似對映表,它還具有如下額外的特性:
原子操作,類似java.util.ConcurrentMap
讀快取
寫快取
快取事件監聽者
統計
包括所有等級的事務處理
快取註釋(譯註:Java的Annotation機制)
泛型快取
存引用和存值的定義
類的載入
快取包含的資料被不同的執行緒共享,這些執行緒可能執行在不同的容器或者OSGi的Bundle中,他們可能在一個JVM中,也可能被分佈在多個JVM的叢集中。這就使得類的載入需要具有技巧性。
我們已經解決了這個問題。當一個CacheManager建立時,我們需要指定一個classloader。如果沒有指定,我們就是用預設的。不管怎樣,物件的反序列化將會用到CacheManager的classloader。
相比Ehcache的落後方式,我們的處理方式是一個很大的進步。首先,執行緒的context classloader將會被使用,如果它失敗了,會嘗試使用另一個classloader。這樣做可以在大多數場景下有效,但是可能還需要根據具體實現做一些小調整和修改。
獲取程式碼
這個規範是以Maven為中心的。Maven配置片段如下
<groupId>javax.cache</groupId>
<artifactId>cache-api</artifactId>
<version>0.3</version>
API使用簡介
建立一個CacheManager
我們支援Java 6 java.util.ServiceLoader的建立方式。它會自動在你的classpath裡偵測一個cache實現。然後你可以這樣建立一個CacheManager:
CacheManager cacheManager = Caching.getCacheManager();
這行程式碼返回一個CacheManager的單例物件,名為“default”。後續的呼叫都將返回相同CacheManager。
CacheManager物件可以有名字和classloader,參考如下:
CacheManager cacheManager = Caching.getCacheManager(“app1”, Thread.currentThread().getContextClassLoader());
實現或許支援直接new的方式來提供最大的靈活性:
CacheManager cacheManager = new RICacheManager(“app1”, Thread.currentThread().getContextClassLoader());
或者在不新增編譯依賴的情況實現同樣的工作:
String className = "javax.cache.implementation.RIServiceProvider";
Class<ServiceProvider> clazz =(Class<ServiceProvider>)Class.forName(className);
ServiceProvider provider = clazz.newInstance();
return provider.createCacheManager(Thread.currentThread().getContextClassLoader(), "app1");
建立一個快取
API支援程式設計方式建立快取。它補充了通常只能按照各供應商的約定,宣告式的配置快取方式。
讓我們通過程式配置一個名為“testCache”的只讀快取:
cacheManager = getCacheManager();
CacheConfiguration cacheConfiguration = cacheManager.createCacheConfiguration()
cacheConfiguration.setReadThrough(true);
Cache testCache = cacheManager.createCacheBuilder(“testCache”)
.setCacheConfiguration(cacheConfiguration).build();
獲取一個快取引用
你可以從CacheManager獲取快取。為了獲取一個名為testCache:
Cache<Integer, Date> cache = cacheManager.getCache(“testCache”);
基礎快取操作
放置一個快取:
Cache<Integer, Date> cache = cacheManager.getCache(cacheName);
Date value1 = new Date();
Integer key = 1;
cache.put(key, value1);
獲取一個快取:
Cache<Integer, Date> cache = cacheManager.getCache(cacheName);
Date value2 = cache.get(key);
刪除一個快取
Cache<Integer, Date> cache = cacheManager.getCache(cacheName);
Integer key = 1;
cache.remove(key);
註釋
JSR107介紹一個標準的快取操作集合,它們在一個執行在依賴注入容器裡的類中,完成方法級的快取注入
。由於Ehcache為Spring實現的註釋(而後影響了Spring 3快取註釋),註釋風格的快取正在變得越來越流行。
JSR107註釋包含的最常用的快取註釋包括:
@CacheResult – 使用cache
@CachePut – 放入cache
@CacheRemoveEntry – 從cache刪除單個條目
@CacheRemoveAll – 從cache刪除所有條目
當需要cache名字時,key和value都可以作為輸入。詳情查閱請JavaDoc。為了允許更精確的控制,你可以指定所有這些或更多。在下面的例子中,cacheName屬性可以被指定為“domainCache”,index可以作為key,domain可以作為value。
public class DomainDao {
@CachePut(cacheName="domainCache")
public void updateDomain(String domainId, @CacheKeyParam int index,
@CacheValue Domain domain) {
...
}
}
這個參考實現包含一個實現支援Spring和CDI。CDI在Java EE 6中的標準的容器驅動的注入器。這個實現 為支援重用,被很好的模組化了,同時使用Apache license,並且我們希望有更多開源快取能夠重用。雖然我們並沒有為Guice完成一個實現,但其實這是很容易完成的。
註釋例項
這個例子展示瞭如何實用註釋來保持一個快取與資料結構的同步(Blog manager的例子),同時使用快取來為response提速(通過使用@CacheResult)。
public class BlogManager {
@CacheResult(cacheName="blogManager")
public Blog getBlogEntry(String title) {...}
@CacheRemoveEntry(cacheName="blogManager")
public void removeBlogEntry(String title) {...}
@CacheRemoveAll(cacheName="blogManager")
public void removeAllBlogs() {...}
@CachePut(cacheName=”blogManager”)
public void createEntry(@CacheKeyParam String title,
@CacheValue Blog blog) {...}
@CacheResult(cacheName="blogManager")
public Blog getEntryCached(String randomArg,
@CacheKeyParam String title){...}
}
Spring例項
在Spring中,關鍵是下面的配置行,它把caching annotation interceptors(快取註釋攔截器)加入到Spring的context中:
<jcache-spring:annotation-driven proxy-target-class="true"/>
一個完成例子:
<beans ...>
<context:annotation-config/>
<jcache-spring:annotation-driven proxy-target-class="true"/>
<bean id="cacheManager" factory-method="getCacheManager" />
</beans>
Spring有它自己的快取註釋方式,它基於早期的JSR107貢獻者Eric Dalquist。那些註釋和JSR107將會很好的共存。
CDI例子
首先建立一個javax.cache.annotation.BeanProvider的實現,然後告訴CDI(在/META-INF/services/的classpath中宣告一個名為javax.cache.annotation.BeanProvider的資源)。
一個使用Weld實現的CDI,參考在我們CDI測試中的CdiBeanProvider。
Further Reading 擴充套件閱讀
更多閱讀請訪問JSR的主頁https://github.com/jsr107/jsr107spec。
檢視英文原文:javax.cache: The new Java Caching Standard
本文參與iTran樂譯專案。
相關文章
- Red Hat為Java EE 7提交新的快取規範標準Java快取
- 原創翻譯-Java 8新特性Java
- [譯] 高效能 Java 快取庫 — CaffeineJava快取
- 用於快取的新HTTP標準:Cache-Status和Target-Cache-Control快取HTTP
- 爬取有道翻譯
- Web新標準Web
- 有道雲詞典--翻譯/螢幕取詞翻譯
- 爬取必應翻譯
- xml.etree.ElementTree 文件中文翻譯; SVG向量圖;Python標準庫XMLSVGPython
- 新標準日語全套學習筆記免費領取筆記
- java 介面(翻譯自Java Tutorials)Java
- Java快取EhcacheJava快取
- Java快取--JCSJava快取
- Java 雙快取Java快取
- 13 Java NIO 管道-翻譯Java
- 1 Java NIO概述-翻譯Java
- [翻譯]Java HashMap工作原理JavaHashMap
- Java高併發快取架構,快取雪崩、快取穿透之謎Java快取架構穿透
- [譯] RxJS 高階快取JS快取
- Java快取淺析Java快取
- 16 Java NIO Files-翻譯Java
- 15 Java NIO Path-翻譯Java
- 12 Java NIO DatagramChannel-翻譯Java
- 17 Java NIO AsynchronousFileChannel-翻譯Java
- 8 Java NIO FileChannel-翻譯Java
- 3 Java NIO Buffer-翻譯Java
- 2 Java NIO Channel-翻譯Java
- JAVA NIO 翻譯系列(七、FileChannel)Java
- [譯] Kotlin 標準方法備忘Kotlin
- Java的標準日誌Java
- 用Java寫一個分散式快取——快取管理Java分散式快取
- 新microsoft.com的故事(翻譯中)ROS
- Delphi6的新特性[翻譯] (轉)
- [譯] HTTP 快取頭部 - 完全指南HTTP快取
- Java Integer的快取策略Java快取
- LRU快取實現(Java)快取Java
- Java快取備忘大全Java快取
- 新標準簡化SOA開發