百度解释:Ehcache是一种广泛使用的开源Java分布式缓存。主要面向通用缓存,Java EE和轻量级容器。它具有内存和磁盘存储,缓存加载器,缓存扩展,缓存异常处理程序,一个gzip缓存servlet过滤器,支持REST和SOAP api等特点。
一、依赖包
pom.xml
<dependency>
<groupId>net.sf.ehcache</groupId>
<artifactId>ehcache</artifactId>
<version>2.10.5</version>
</dependency>
二、配置文件
ehcache.xml
<?xml version="1.0" encoding="UTF-8"?>
<ehcache>
<!--timeToIdleSeconds 当缓存闲置n秒后销毁 -->
<!--timeToLiveSeconds 当缓存存活n秒后销毁 -->
<!--
缓存配置
name:缓存名称。
maxElementsInMemory:缓存最大个数。
eternal:对象是否永久有效,一但设置了,timeout将不起作用。
timeToIdleSeconds:设置对象在失效前的允许闲置时间(单位:秒)。仅当eternal=false对象不是永久有效时使用,可选属性,默认值是0,也就是可闲置时间无穷大。
timeToLiveSeconds:设置对象在失效前允许存活时间(单位:秒)。最大时间介于创建时间和失效时间之间。仅当eternal=false对象不是永久有效时使用,默认是0.,也就是对象存活时间无穷大。
overflowToDisk:当内存中对象数量达到maxElementsInMemory时,Ehcache将会对象写到磁盘中。
diskSpoolBufferSizeMB:这个参数设置DiskStore(磁盘缓存)的缓存区大小。默认是30MB。每个Cache都应该有自己的一个缓冲区。
maxElementsOnDisk:硬盘最大缓存个数。
diskPersistent:是否缓存虚拟机重启期数据 Whether the disk store persists between restarts of the Virtual Machine. The default value is false.
diskExpiryThreadIntervalSeconds:磁盘失效线程运行时间间隔,默认是120秒。
memoryStoreEvictionPolicy:当达到maxElementsInMemory限制时,Ehcache将会根据指定的策略去清理内存。默认策略是LRU(最近最少使用)。你可以设置为FIFO(先进先出)或是LFU(较少使用)。
clearOnFlush:内存数量最大时是否清除。
-->
<!-- 指定一个文件目录,当EhCache把数据写到硬盘上时,将把数据写到这个文件目录下 -->
<diskStore path="C:/Users/infi/Desktop"/>
<!-- 设定缓存的默认数据过期策略 -->
<defaultCache
maxElementsInMemory="10000"
eternal="false"
overflowToDisk="true"
timeToIdleSeconds="10"
timeToLiveSeconds="20"
diskPersistent="false"
diskExpiryThreadIntervalSeconds="120"/>
<cache name="cacheTest"
maxElementsInMemory="1000"
eternal="false"
overflowToDisk="true"
timeToIdleSeconds="10"
timeToLiveSeconds="20"/>
</ehcache>
注意:timeToIdleSeconds 和 timeToLiveSeconds,这两个参数设置的是10和20,等下针对它们进行测试。
applicationContext.xml,里面引入了ehcache.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:cache="http://www.springframework.org/schema/cache"
xsi:schemaLocation="http://www.springframework.org/schema/cache http://www.springframework.org/schema/cache/spring-cache-4.1.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.1.xsd">
<context:component-scan base-package="com.zhuyun"/>
<cache:annotation-driven cache-manager="cacheManager" />
<bean id="cacheManager" class="org.springframework.cache.ehcache.EhCacheCacheManager">
<property name="cacheManager" ref="ehcache"></property>
</bean>
<bean id="ehcache" class="org.springframework.cache.ehcache.EhCacheManagerFactoryBean">
<property name="configLocation" value="ehcache.xml"></property>
</bean>
</beans>
三、实现代码
EhCacheTestService.java
package com.zhuyun.ehcache;
public interface EhCacheTestService {
public String getTimestamp(String param);
}
该接口很简单,根据一个参数,获取返回值。下面是实现类:
EhCacheTestServiceImpl.java
package com.zhuyun.ehcache;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
@Service("ehCacheTestService")
public class EhCacheTestServiceImpl implements EhCacheTestService {
@Cacheable(value="cacheTest",key="#param")
public String getTimestamp(String param) {
Long timestamp = System.currentTimeMillis();
return timestamp.toString();
}
}
该类需要使用@Cacheable注释,value的值cacheTest即是ehcache.xml配置文件中设置的缓存策略。
四、测试类
EhCacheTestServiceTest.java
package com.zhuyun.ehcache;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class EhCacheTestServiceTest{
public static void main(String[] args) {
try {
ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
EhCacheTestService ehCacheTestService = (EhCacheTestService) context.getBean("ehCacheTestService");
//测试当缓存闲置10秒后销毁
System.out.println("第一次调用:" + ehCacheTestService.getTimestamp("param"));
Thread.sleep(2000);
System.out.println("2秒之后调用:" + ehCacheTestService.getTimestamp("param"));
Thread.sleep(11000);
System.out.println("再过11秒之后调用:" + ehCacheTestService.getTimestamp("param"));
System.out.println();
//当缓存存活20秒后销毁
System.out.println("第一次调用另一个参数:" + ehCacheTestService.getTimestamp("param2"));
Thread.sleep(5000);
System.out.println("5秒后调用一次:" + ehCacheTestService.getTimestamp("param2"));
Thread.sleep(5000);
System.out.println("10秒后调用一次:" + ehCacheTestService.getTimestamp("param2"));
Thread.sleep(5000);
System.out.println("15秒后调用一次:" + ehCacheTestService.getTimestamp("param2"));
Thread.sleep(6000);
System.out.println("21秒后调用一次:" + ehCacheTestService.getTimestamp("param2"));
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
测试结果如下:
从ehcache.xml文件中,我们设置了timeToIdleSeconds="10",意思是当缓存闲置10秒后销毁 。上图中可以看出,在10秒内我们使用相同的参数调用时,返回的结果是相同的,所以结果是从缓存中直接拿出来的。
另外,我们也设置了timeToLiveSeconds="20",意思是当缓存存活20秒后销毁,即使缓存一直被使用,过了20秒一样会被销毁。从上图中也可以看出,虽然我们每过5秒调用一次,20秒之后,缓存依然不存在了。