BigMemory系列文章--2.Ehcache快速接入

转载请注明出处哈:http://carlosfu.iteye.com/blog/2237511


 

一、依赖

 

1. ehcache依赖

<ehcache.version>2.6.11</ehcache.version>
<dependency>
    <groupId>net.sf.ehcache</groupId>
    <artifactId>ehcache-core</artifactId>
    <version>${ehcache.version}</version>
</dependency>

 

 2. ehcache依赖树: mvn dependency:tree

[INFO] \- net.sf.ehcache:ehcache-core:jar:2.6.11:compile
[INFO] \- org.slf4j:slf4j-api:jar:1.7.5:compile

 

3. 由于slf4j-api是日志接口,加入具体实现logback(log4j也可以)

 

<logback.version>1.0.13</logback.version>
<dependency>
    <groupId>ch.qos.logback</groupId>
    <artifactId>logback-core</artifactId>
    <version>${logback.version}</version>
</dependency>
<dependency>
    <groupId>ch.qos.logback</groupId>
    <artifactId>logback-classic</artifactId>
    <version>${logback.version}</version>
</dependency> 

 

 4. 为了方便单元测试,引入junit

<junit.version>4.11</junit.version>
<dependency>
   <groupId>junit</groupId>
   <artifactId>junit</artifactId>
   <version>${junit.version}</version>
</dependency>

 

最终pom: 

<properties>
       <ehcache.version>2.6.11</ehcache.version>
       <logback.version>1.0.13</logback.version>
       <junit.version>4.11</junit.version>
   </properties>
   <dependencies>
       <dependency>
           <groupId>ch.qos.logback</groupId>
           <artifactId>logback-core</artifactId>
           <version>${logback.version}</version>
       </dependency>
       <dependency>
           <groupId>ch.qos.logback</groupId>
           <artifactId>logback-classic</artifactId>
           <version>${logback.version}</version>
       </dependency>
       <dependency>
           <groupId>junit</groupId>
           <artifactId>junit</artifactId>
           <version>${junit.version}</version>
       </dependency>
       <dependency>
           <groupId>net.sf.ehcache</groupId>
           <artifactId>ehcache-core</artifactId>
           <version>${ehcache.version}</version>
       </dependency>
   </dependencies>
   <build>
       <plugins>
           <plugin>
               <groupId>org.apache.maven.plugins</groupId>
               <artifactId>maven-compiler-plugin</artifactId>
               <version>3.1</version>
               <configuration>
                   <source>1.7</source>
                   <target>1.7</target>
                   <encoding>UTF-8</encoding>
               </configuration>
           </plugin>
       </plugins>
   </build>

 

二、ehcache配置

 

注意:如果不添加,会使用ehcache-core-2.6.11.jar下的ehcache-failsafe.xml作为默认配置

一般来说需要把ehcache.xml放到classpath下:我们使用极简配置

<?xml version="1.0" encoding="UTF-8" ?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:noNamespaceSchemaLocation="http://ehcache.org/ehcache.xsd">
    <cache name="firstEhcache" maxElementsInMemory="10000">
    </cache>
</ehcache>

 

三、logback配置

<?xml version="1.0" encoding="UTF-8"?>
<configuration scan="true" scanPeriod="5 seconds">
    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern>
        </encoder>
    </appender>
    <root level="INFO">
        <appender-ref ref="STDOUT"/>
    </root>
</configuration>

 

四、单元测试

1. 一个实体类:

package com.sohu.tv.ehcache.first;
import java.util.Date;
/**
 * 俱乐部
 * 
 * @author leifu
 * @Date 2015年7月28日
 * @Time 下午1:43:53
 */
public class Club {
    /**
     * 俱乐部id
     */
    private int id;
    /**
     * 俱乐部名
     */
    private String clubName;
    /**
     * 俱乐部描述
     */
    private String clubInfo;
    /**
     * 创建日期
     */
    private Date createDate;
    /**
     * 排名
     */
    private int rank;
    public Club(int id, String clubName, String clubInfo, Date createDate, int rank) {
        super();
        this.id = id;
        this.clubName = clubName;
        this.clubInfo = clubInfo;
        this.createDate = createDate;
        this.rank = rank;
    }
    public Club() {
        super();
    }
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public String getClubName() {
        return clubName;
    }
    public void setClubName(String clubName) {
        this.clubName = clubName;
    }
    public String getClubInfo() {
        return clubInfo;
    }
    public void setClubInfo(String clubInfo) {
        this.clubInfo = clubInfo;
    }
    public Date getCreateDate() {
        return createDate;
    }
    public void setCreateDate(Date createDate) {
        this.createDate = createDate;
    }
    public int getRank() {
        return rank;
    }
    public void setRank(int rank) {
        this.rank = rank;
    }
    @Override
    public String toString() {
        return "Club [id=" + id + ", clubName=" + clubName + ", clubInfo=" + clubInfo + ", createDate=" + createDate
                + ", rank=" + rank + "]";
    }
}

 

2. 单元测试:

package com.sohu.tv.ehcache.first;
import java.util.Date;
import org.junit.BeforeClass;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import net.sf.ehcache.Cache;
import net.sf.ehcache.CacheManager;
import net.sf.ehcache.Element;
/**
 * 第一个ehcache测试
 * 
 * @author leifu
 * @Date 2015年8月12日
 * @Time 上午10:14:13
 */
public class FirstEhcacheTest {
    private static Logger logger = LoggerFactory.getLogger(FirstEhcacheTest.class);
    private static Cache cache;
    @BeforeClass
    public static void setUp() {
        CacheManager cacheManager = CacheManager.create(FirstEhcacheTest.class.getClassLoader().getResourceAsStream("ehcache.xml"));
        // 打印cacheManager管理的cache
        String[] cacheNameArr = cacheManager.getCacheNames();
        for (String cacheName : cacheNameArr) {
            logger.info("cacheName: {}", cacheName);
        }
        cache = cacheManager.getCache("firstEhcache");
    }
    @Test
    public void testCRUD() {
        logger.info("At start, ehcache object size: {}", cache.getSize());
        // 唯一key
        String key = "football:club:1";
        Club club = new Club(1, "AC", "AC米兰", new Date(), 1);
        // 增
        Element element = new Element(key, club);
        cache.put(element);
        logger.info("after add ehcache object size: {}", cache.getSize());
        // 查
        Element elementResult = cache.get(key);
        Club clubResult = (Club) elementResult.getObjectValue();
        logger.info("get key {} value is {}", key, clubResult.toString());
        // 修改
        club.setRank(8888);
        cache.put(element);
        logger.info("after set ehcache object size: {}", cache.getSize());
        // 再查
        Element elementResultAgain = cache.get(key);
        Club clubResultAgain = (Club) elementResultAgain.getObjectValue();
        logger.info("get key {} again value is {}", key, clubResultAgain.toString());
        // 删
        boolean removeResult = cache.remove(key);
        logger.info("remove result is {}, after remove ehcache object size: {}", removeResult, cache.getSize());
        // 增加一条,观察下次启动
        cache.put(element);
        logger.info("At final, ehcache object size: " + cache.getSize());
        // 生产环境不要使用,影响性能
        logger.info("At final, ehcache memory size: " + cache.calculateInMemorySize());
    }
}

 五、输出:

10:43:11.405 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - cacheName: firstEhcache
10:43:11.410 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - At start, ehcache object size: 0
10:43:11.413 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - after add ehcache object size: 1
10:43:11.416 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - get key football:club:1 value is Club [id=1, clubName=AC, clubInfo=AC米兰, createDate=Wed Aug 12 10:43:11 CST 2015, rank=1]
10:43:11.416 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - after set ehcache object size: 1
10:43:11.417 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - get key football:club:1 again value is Club [id=1, clubName=AC, clubInfo=AC米兰, createDate=Wed Aug 12 10:43:11 CST 2015, rank=8888]
10:43:11.417 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - remove result is true, after remove ehcache object size: 0
10:43:11.417 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - At final, ehcache object size: 1
10:43:11.418 [main] INFO c.s.t.ehcache.first.FirstEhcacheTest - At final, ehcache memory size: 1

 

六、结论、注意、猜想:

1. 如果没有配置diskStore作为持久化数据源,每次启动时候ehcache都是空的(因为ehcache是进程内缓存,会伴随着JVM的结束而消失)

2. ehcache接口中 put代表了add和set。

3. 官方文档中说:cache.calculateInMemorySize()这个方法不要在生产环境中使用,会影响性能。

4. Ehcache的增删改查API使用十分简单。

Ehcache优化配置相当多:各个层级数据容量大小、key过期策略算法、overFlow策略、序列化等等。

 

 

上一篇:BigMemory系列文章--3. Ehcache存储层级(tier)


下一篇:BigMemory系列文章--目录