下面是关于Eviction和Expiration的注意点:
- Expiration是一个顶层结构,可以通过配置或者cache API定义。之后我们会有更多的阐述。
- Eviction针对的是本地缓存实例,Expiration针对的则是整个集群范围内的节点。Expiration的lifespan和maxIdle的值会在缓存每个数据项间进行复制。
- Expiration的lifespan和maxIdle的值会持久化到CacheStores,所以这些信息也能够被eviction或者passivation使用。
- Infinispan包含了三种eviction策略, EvictionStrategy.NONE, EvictionStrategy.LRU 和EvictionStrategy.FIFO,并且这些都是最有用的。如果需要,将来还会增加更多的策略。
- 从 Infinispan 4.1版本开始, EvictionStrategy.UNORDERED 将会可用。
- 从架构上讲,这些是完全新的实现。
配置
Eviction可以通过Configuration bean 或者XML文件的方式进行配置。 Eviction配置是基于单个缓存的。 关于Eviction的有用配置元素包括:
<eviction strategy="FIFO" wakeupInterval="1000" maxEntries="2000"/> <expiration lifespan="1000" maxIdle="500" />
通过编程方式,可以达到同样的效果:
configuration.setEvictionStrategy(EvictionStrategies.FIFO); configuration.setEvictionWakeupInterval(1000); configuration.setEvictionMaxEntries(2000); configuration.setExpirationLifespan(1000); configuration.setExpirationMaxIdle(500);
默认值
默认情况下,Eviction是没有启用的。 如果启用了Eviction (通过一个空白的 <eviction /> 元素),将会使用一定的默认值:
- strategy: 如果没有指定策略,将会默认使用EvictionStrategy.NONE。
- wakeupInterval: 如果没有指定,默认值是5000。
- 如果你想要禁用 eviction 线程,可以设置wakeupInterval值为 -1。
- maxEntries: 如果没有指定,默认值是-1,意味着包含无限个数据项。
- 0 意味着没有数据项,eviction 将会一直使缓存为空。
Eviction的lifespan 和maxIdle值默认为 -1。
Expiration的使用
你可以为缓存中的任意键值对设置一个Expiration的lifespan和maxIdle的值。它即可以像上面所说的那样通过配置设置成集群范围的,也可以使用Cache接口来定义键值对。任何键值对定义的值都能够覆写该数据项在集群范围内的默认值。
例如使用下面的配置:
<expiration lifespan="1000" />
// this entry will expire in 1000 millis cache.put("pinot noir", pinotNoirPrice); // this entry will expire in 2000 millis cache.put("chardonnay", chardonnayPrice, 2, TimeUnit.SECONDS); // this entry will expire 1000 millis after it is last accessed cache.put("pinot grigio", pinotGrigioPrice, -1, TimeUnit.SECONDS, 1, TimeUnit.SECONDS); // this entry will expire 1000 millis after it is last accessed, or // in 5000 millis, which ever triggers first cache.put("riesling", rieslingPrice, 5, TimeUnit.SECONDS, 1, TimeUnit.SECONDS);
Eviction 设计
Eviction的核心是一个 EvictionManager实例 。如果配置了Eviction或者Expiration,则这个实例是可用的。
EvictionManager的作用就是 eviction线程which periodically purges items from the DataContainer. 如果禁用了eviction线程(wakeupInterval设置为-1) ,eviction可以通过调用EvictionManager.processEviction()来手动启动,例如通过周期性的运行应用中的另一条维护线程。
eviction manager是按照下面的方式来处理evictions的:
- 触发Data Container清除过期的数据项
- 触发Cache Stores (如果存在的话) 清除过期数据项
- 调整Data Container的大小为指定值,该值的大小有maxElements属性决定
DataContainer
DataContainer 是缓存和Eviction的核心。因此,使用哪种DataContainer接口的实现决定于是否启用了eviction和使用了哪种eviction策略。DataContainer提供了类似purgeExpired() 和iterator()的方法,这些方法会在上述步骤1 和步骤3由EvictionManager调用。
如果缓存不启用Eviction,那么效率最高的data container实现就是SimpleDataContainer。 FIFOSimpleDataContainer 和 LRUSimpleDataContainer 实现会在排序上消耗一定的性能。关于算法的细节可以参照实现的 Javadocs。
評論