ehcache
本地缓存Ehcache
什么是Ehcache
Ehcache是纯java的开源缓存框架,具有快速、精干等特点,是Hibernate中默认的CacheProvider。它主要面向通用缓存、Java EE和轻量级容器,具有内存和磁盘存储、缓存加载器、缓存扩展、缓存异常处理程序。
Ehcache最初由Greg Luck于2003年开始开发。2009年,该项目被Terracotta购买。软件仍然开源,但一些新的主要功能(例如,快速可重启性之间的一致性的)只能在商业产品中使用。
Ehcache 被广泛用于在Hibernate、Spring、Cocoon等其他开源系统。
Ehcache的主要特性
1.快速;
2.简单;
3.多种缓存策略;
4.缓存数据有两级:内存和磁盘,因此无需担心容量问题;
5.缓存数据会在虚拟机重启的过程中写入磁盘;
6.可以通过 RMI、可插入 API 等方式进行分布式缓存;
7.具有缓存和缓存管理器的侦听接口;
8.支持多缓存管理器实例,以及一个实例的多个缓存区域;
9.提供 Hibernate 的缓存实现;
Ehcache使用介绍
Ehcache是用来管理缓存的一个工具,其缓存的数据可以是存放在内存里面的,也可以是存放在硬盘上的。其核心是CacheManager,一切Ehcache的应用都是从CacheManager开始的。它是用来管理Cache(缓存)的,一个应用可以有多个CacheManager,而一个CacheManager下又可以有多个Cache。Cache内部保存的是一个个的Element,而一个Element中保存的是一个key和value的配对,相当于Map里面的一个Entry。
Ehcache缓存过期策略
当缓存需要被清理时(比如空间占用已经接近临界值了),需要使用某种淘汰算法来决定清理掉哪些数据。常用的淘汰算法有下面几种:
FIFO:First In First Out,先进先出。判断被存储的时间,离目前最远的数据优先被淘汰。
LRU:Least Recently Used,最近最少使用。判断最近被使用的时间,目前最远的数据优先被淘汰。
LFU:Least Frequently Used,最不经常使用。在一段时间内,数据被使用次数最少的,优先被淘汰。
解决缓存与db不同步
ehcache配置
ehcache.xml
<?xml version="1.0" encoding="UTF-8"?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="http://ehcache.org/ehcache.xsd">
<diskStore path="java.io.tmpdir/ehcache-rmi-4000" />
<!-- 默认缓存 -->
<defaultCache maxElementsInMemory="1000" eternal="true"
timeToIdleSeconds="120" timeToLiveSeconds="120" overflowToDisk="true"
diskSpoolBufferSizeMB="30" maxElementsOnDisk="10000000"
diskPersistent="true" diskExpiryThreadIntervalSeconds="120"
memoryStoreEvictionPolicy="LRU">
</defaultCache>
<!-- demo缓存 -->
<cache name="userCache" maxElementsInMemory="1000" eternal="false"
timeToIdleSeconds="120" timeToLiveSeconds="120" overflowToDisk="true"
diskSpoolBufferSizeMB="30" maxElementsOnDisk="10000000"
diskPersistent="false" diskExpiryThreadIntervalSeconds="120"
memoryStoreEvictionPolicy="LRU">
<cacheEventListenerFactory
class="net.sf.ehcache.distribution.RMICacheReplicatorFactory" />
<!-- 用于在初始化缓存,以及自动设置 -->
<bootstrapCacheLoaderFactory
class="net.sf.ehcache.distribution.RMIBootstrapCacheLoaderFactory" />
</cache>
</ehcache>
启动配置文件
#### 端口号
server:
port: 8080
### 数据库
spring:
datasource:
url: jdbc:mysql://localhost:3306/jeremy?useSSL=false&serverTimezone=UTC
driver-class-name: com.mysql.cj.jdbc.Driver
username: root
password: 123
## 缓存配置读取
cache:
type: ehcache
ehcache:
config: classpath:ehcache.xml
启动类配置
package com.ehcache.demo;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.cache.annotation.EnableCaching;
//@SpringBootApplication(exclude= {DataSourceAutoConfiguration.class}) 没有配置数据库的时候用
@SpringBootApplication
@MapperScan(basePackages = {"com.ehcache.demo.mapper"})
@EnableCaching //表示开启缓存
public class DemoApplication {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
}
controller 类
package com.ehcache.demo.controller;
import com.ehcache.demo.cache.MapCache;
import com.ehcache.demo.model.User;
import com.ehcache.demo.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.CacheManager;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class IndexController {
@Autowired
private MapCache<String,Object> mapCache;
@Autowired
private UserService userService;
@Autowired
private CacheManager cacheManager;
@RequestMapping("/remoKey")
public void remoKey(){
cacheManager.getCache("userCache").clear();
}
@RequestMapping("/getUser")
public User getUser(Long id){
return userService.getUser(id);
}
@RequestMapping("/get")
public String get(String key){
return (String) mapCache.get(key);
}
@RequestMapping("/put")
public String put(String key,String value){
mapCache.put(key,value);
return "success";
}
@RequestMapping("/remove")
public String remove(String key){
mapCache.remove(key);
return "success";
}
}
service层就不写了直接写mapper层
package com.ehcache.demo.mapper;
import com.ehcache.demo.model.User;
import org.apache.ibatis.annotations.Select;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Repository;
//@CacheConfig配置缓存基本信息 cacheNames缓存名称
//@Cacheable 该方法查询数据库完毕之后,存入到缓存中
@CacheConfig(cacheNames = {"userCache"}) //配置缓存的基本信息
public interface UserMapper {
@Select("SELECT ID,NAME,AGE from ehcacheTest where id = #{id}")
@Cacheable
User getUser(Long id);
}