注解 | 描述 |
---|---|
Cache | 缓存接口,定义缓存操作。实现有:RedisCache、EhCacheCache、ConcurrentMapCache等 |
CacheManager | 缓存管理器,管理各种缓存(Cache)组件 |
@Cacheable | 主要针对方法配置,能够根据方法的请求参数对其结果进行缓存 |
@CacheEvict | 清空缓存 |
@CachePut | 保证方法被调用,又希望结果被缓存。 |
@EnableCaching | 开启基于注解的缓存 |
keyGenerator | 缓存数据时key生成策略 |
serialize | 缓存数据时value序列化策略 |
参数 | 描述 | 例子 |
---|---|---|
value | 缓存的名称,在 spring 配置文件中定义,必须指定至少一个 | @Cacheable(value={”cache1”,”cache2”} |
key | 缓存的 key,可以为空,如果指定要按照 SpEL 表达式编写,如果不指定,则缺省按照方法的所有参数进行组合 | @Cacheable(value=”testcache”,key=”#userName”) |
condition | 缓存的条件,可以为空,使用 SpEL 编写,返回 true 或者 false,只有为 true 才进行缓存/清除缓存,在调用方法之前之后都能判断 | @Cacheable(value=”testcache”,condition=”#userName.length()>2”) |
allEntries(@CacheEvict ) | 是否清空所有缓存内容,缺省为 false,如果指定为 true,则方法调用后将立即清空所有缓存 | @CachEvict(value=”testcache”,allEntries=true) |
beforeInvocation(@CacheEvict) | 是否在方法执行前就清空,缺省为 false,如果指定为 true,则在方法还没有执行的时候就清空缓存,缺省情况下,如果方法执行抛出异常,则不会清空缓存 | @CachEvict(value=”testcache”,beforeInvocation=true) |
unless(@CachePut/@Cacheable) | 用于否决缓存的,不像condition,该表达式只在方法执行之后判断,此时可以拿到返回值result进行判断。条件为true不会缓存,fasle才缓存 | @Cacheable(value=”testcache”,unless=”#result == null”) |
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-cacheartifactId>
dependency>
<dependency>
<groupId>org.projectlombokgroupId>
<artifactId>lombokartifactId>
dependency>
dependencies>
主启动类标注@EnableCaching
User.java
package com.hf.cache.entity;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import lombok.experimental.Accessors;
import java.io.Serializable;
/**
* @Copyright (C), 2016-2019 hf
* @FileName: User
* @Author: hf
* @Date: 2019/9/29 0:53
* @Description: User 实体
*/
@Getter
@Setter
@Accessors(chain = true)
@AllArgsConstructor
@ToString
public class User implements Serializable {
//id
private String id;
//用户名
private String name;
//手机号
private String phone;
//邮箱
private String email;
//状态
private boolean status;
}
package com.hf.cache.service;
import com.hf.cache.entity.User;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.cache.annotation.Caching;
import org.springframework.stereotype.Service;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
/**
* @Copyright (C), 2016-2019 hf
* @FileName: UserService
* @Author: hf
* @Date: 2019/9/29 0:57
* @Description: 用户服务实现层
*/
@Service
public class UserService {
static Map<String, User> map = new HashMap<>(12);
static {
map.put("liuyi", new User(UUID.randomUUID().toString().substring(0,7), "liuyi", "155********", "[email protected]", true));
map.put("chenger", new User(UUID.randomUUID().toString().substring(0,7), "chenger", "166********", "[email protected]", true));
map.put("zhangsan", new User(UUID.randomUUID().toString().substring(0,7), "zhangsan", "165********", "[email protected]", true));
map.put("lisi", new User(UUID.randomUUID().toString().substring(0,7), "lisi", "178********", "[email protected]", true));
map.put("wangwu", new User(UUID.randomUUID().toString().substring(0,7), "wangwu", "182********", "[email protected]", true));
}
/**
* 功能描述:
* 查询用户实体并缓存
* 〈
* 相关参数说明:
* cacheNames/value:指定缓存组件的名字;将方法的返回结果放在哪个缓存中,是数组的方式,可以指定多个缓存;
*
* key:缓存数据使用的key;可以用它来指定。默认是使用方法参数的值 1-方法的返回值
* 编写SpEL; #i d;参数id的值 #a0 #p0 #root.args[0]
* getEmp[2]
*
* keyGenerator:key的生成器;可以自己指定key的生成器的组件id
* key/keyGenerator:二选一使用;
*
*
* cacheManager:指定缓存管理器;或者cacheResolver指定获取解析器
*
* condition:指定符合条件的情况下才缓存;
* ,condition = "#id>0"
* condition = "#a0>1":第一个参数的值》1的时候才进行缓存
*
* unless:否定缓存;当unless指定的条件为true,方法的返回值就不会被缓存;可以获取到结果进行判断
* unless = "#result == null"
* unless = "#a0==2":如果第一个参数的值是2,结果不缓存;
* sync:是否使用异步模式
*
* 〉
*
* @className: UserService
* @author: hf
* @version: 1.0.0
* @date: 2019/9/29 1:10
* @param: [key]
* @return: com.hf.cache.entity.User
*
*/
@Cacheable(value = {"user"},key = "#key",unless = "#result==null")
public User getUser(String key) {
System.out.println("查询key=【" + key + "】的用户");
return map.get(key);
}
/**
* 功能描述:
* 〈
* 更新用户信息
* @CachePut:既调用方法,又更新缓存数据;同步更新缓存
* 〉
*
* @className: UserService
* @author: hf
* @version: 1.0.0
* @date: 2019/9/29 1:15
* @param: [user]
* @return: com.hf.cache.entity.User
*
*/
@CachePut(value = {"user"},key = "#result.name")
public User updateUser(User user) {
map.put(user.getName(), user);
return user;
}
/**
* 功能描述:
* 〈
* 删除用户
* @CacheEvict:缓存清除
*
* key:指定要清除的数据
* allEntries = true:指定清除这个缓存中所有的数据
* beforeInvocation = false:缓存的清除是否在方法之前执行
* 默认代表缓存清除操作是在方法执行之后执行;如果出现异常缓存就不会清除
* beforeInvocation = true:
* 代表清除缓存操作是在方法运行之前执行,无论方法是否出现异常,缓存都清除
*
* 〉
*
* @className: UserService
* @author: hf
* @version: 1.0.0
* @date: 2019/9/29 1:20
* @param: [key]
* @return: void
*
*/
@CacheEvict(value = {"user"},beforeInvocation = true)
public void deleteUser(String key) {
map.remove(key);
}
/**
* 功能描述:
* 〈
* @Caching 定义复杂的缓存规则
* 〉
*
* @className: UserService
* @author: hf
* @version: 1.0.0
* @date: 2019/9/29 1:25
* @param: [key]
* @return: com.hf.cache.entity.User
*
*/
@Caching(
cacheable = {
@Cacheable(value = "user",key="#key+1")
},
put = {
@CachePut(value = "user",key = "#result.id")
}
)
public User getUserByKey(String key) {
return map.get(key);
}
}
package com.hf.cache.controller;
import com.hf.cache.entity.User;
import com.hf.cache.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;
import java.util.UUID;
/**
* @Copyright (C), 2016-2019 hf
* @FileName: UserController
* @Author: hf
* @Date: 2019/9/29 1:32
* @Description:
*/
@RestController
public class UserController {
@Autowired
UserService userService;
@GetMapping("/get/{key}")
public User get(@PathVariable String key) {
return userService.getUser(key);
}
@GetMapping("/del/{key}")
public String del(@PathVariable String key) {
userService.deleteUser(key);
return "Success";
}
@GetMapping("/upd/{key}")
public User upd(@PathVariable String key) {
User user = new User(UUID.randomUUID().toString(), key, "120000", "[email protected]", true);
return userService.updateUser(user);
}
}