前言:Caffeine 是个高性能的开源 Java 内存缓存库,具有较高的命中率和出色的并发能力。在 Spring Boot 中集成也非常简单,提供了各种开箱既用的工具。
Caffeine 并不是分布式缓存.
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-cache</artifactId>
</dependency>
<dependency>
<groupId>com.github.ben-manes.caffeine</groupId>
<artifactId>caffeine</artifactId>
</dependency>
<dependency>
<groupId>com.github.ben-manes.caffeine</groupId>
<artifactId>caffeine</artifactId>
<version>2.8.0</version>
</dependency>
spring.cache.cache-names=IZUUL
spring.cache.caffeine.spec=initialCapacity=50,maximumSize=500,expireAfterWrite=5s
spring.cache.type=caffeine
Caffeine配置说明:
1、initialCapacity=[integer]: 初始的缓存空间大小
2、maximumSize=[long]: 缓存的最大条数
3、maximumWeight=[long]: 缓存的最大权重
4、expireAfterAccess=[duration]: 最后一次写入或访问后经过固定时间过期
5、expireAfterWrite=[duration]: 最后一次写入后经过固定时间过期
6、refreshAfterWrite=[duration]: 创建缓存或者最近一次更新缓存后经过固定的时间间隔,刷新缓存
7、weakKeys: 打开key的弱引用
8、weakValues:打开value的弱引用
9、softValues:打开value的软引用
1o、recordStats:开发统计功能
注意:
1、expireAfterWrite和expireAfterAccess同时存在时,以expireAfterWrite为准。
2、maximumSize和maximumWeight不可以同时使用
3、weakValues和softValues不可以同时使用
@Configuration
public class CaffeineConfig {
@Bean
public CacheManager caffeineCacheManager() {
SimpleCacheManager cacheManager = new SimpleCacheManager();
List<CaffeineCache> caffeineCaches = new ArrayList<>();
for (CacheType cacheType : CacheType.values()) {
caffeineCaches.add(new CaffeineCache(cacheType.name(),
Caffeine.newBuilder()
.expireAfterWrite(cacheType.getExpires(), TimeUnit.SECONDS)
.build()));
}
cacheManager.setCaches(caffeineCaches);
return cacheManager;
}
}
加入过期时间expires, 分别设置IZUUl消亡时间是 10s, MUMU 消亡时间 5s
public enum CacheType {
IZUUL(10),//消亡时间
MUMU(5);
private int expires;
CacheType(int expires) {
this.expires = expires;
}
public int getExpires() {
return expires;
}
}
5、创建service类
@Service
@Slf4j
public class CaffeineService {
private final static Logger log = LoggerFactory.getLogger(CaffeineService.class);
@Autowired
private CouponUseRecordMapper couponUseRecordMapper;
@Autowired
private FullReductionProductstoreRelaMapper fullReductionProductMapper;
/**
* 根据用户id和优惠券id获取该用户的优惠券记录
*
* @param userId 用户id
* @param couponId 优惠券id
* @return
*/
@Cacheable(value = "IZUUL", key = "#userId.concat(#couponId)")
public long couponUseRecordCount(String userId, String couponId) {
CouponUseRecordCriteria qr = new CouponUseRecordCriteria();
qr.or().andUserIdEqualTo(userId).andCouponIdEqualTo(couponId)
.andCreateTimeGreaterThanOrEqualTo(Utils.getStartTime()).andCreateTimeLessThanOrEqualTo(Utils.getEndTime());
Long i = this.couponUseRecordMapper.countByExample(qr);
log.info("********调用了优惠券使用记录的缓存,用户id{},优惠券id{}********",userId,couponId);
return i;
}
/**
* 根据优惠券id和门店code获取满减券门店产品数据对应的关系
*
* @param couponId 优惠券id
* @param storeCode 门店code
* @param fullReduction 满减类型
* @return
*/
@Cacheable(value = "IZUUL", key = "#couponId.concat(#storeCode).concat(#fullReduction)")
public List<FullReductionProductstoreRela> getFullReductionList(String couponId, String storeCode, String fullReduction) {
FullReductionProductstoreRelaCriteria qr = new FullReductionProductstoreRelaCriteria();
qr.or().andCouponIdEqualTo(couponId).andStoreCodeEqualTo(storeCode);
List<FullReductionProductstoreRela> list = this.fullReductionProductMapper.selectByExample(qr);
log.info("******调用了满减券门店产品数据对应关系的缓存,优惠券id{},门店编码{},满减类型{}*******",couponId,storeCode,fullReduction);
return list;
}
}
@RestController
public class CaffeineController {
@Autowired
private CaffeineService caffeineService;
@PostMapping("/cache-izuul/query")
public boolean isUseCouponNums(
@RequestParam(required = true)User user,
@RequestParam(required = true)ValueCoupon coupon
) {
long i = caffeineService.couponUseRecordCount(user.getUserId(), coupon.getCouponId());
if (i < coupon.getUseNumber()) {
return true;
}
return false;
}
@PostMapping("/cache-izuul/query2")
public FullReductionProductstoreRela queryFullReductionProductstoreRela(
@RequestParam(required = true) String storeCode,
@RequestParam(required = true)String couponId
) {
List<FullReductionProductstoreRela> list = caffeineService.getFullReductionList(couponId, storeCode,"FULL_REDUCTION");
if (CollectionUtils.isNotEmpty(list)) {
return list.get(0);
} else {
return null;
}
}
}
因为最近业务中涉及的查询操作非常多,所以就想到引入缓存这一操作去减轻访问数据库的压力,在网上看了一下相关文章,感觉还是相对比较简单且实用的,所以就简单整理了一下!如果有哪里存在缺陷,望大佬们多多指教!