caffeine:咖啡因属于本地一级缓存,缓存与程序在一个进程里,是基于JVM的缓存
添加依赖
<!--caffeine缓存-->
<dependency>
<groupId>com.github.ben-manes.caffeine</groupId>
<artifactId>caffeine</artifactId>
<version>2.8.6</version>
</dependency>
一、定义缓存接口
package com.jx.bas.console.cache;
import com.github.benmanes.caffeine.cache.LoadingCache;
import java.util.Map;
public interface ICacheManager<T> {
T get(String key);
void put(String key, T value);
void del(String key);
void refresh(Map<String,T> payLoad);
LoadingCache<String, T> getCache();
}
缓存实现类
package com.jx.bas.console.cache;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.github.benmanes.caffeine.cache.CacheWriter;
import com.github.benmanes.caffeine.cache.Caffeine;
import com.github.benmanes.caffeine.cache.LoadingCache;
import com.github.benmanes.caffeine.cache.RemovalCause;
import com.jx.bas.console.modules.zy.dao.UserCaffeineMapper;
import com.jx.bas.console.modules.zy.entity.UserCaffeine;
import lombok.extern.slf4j.Slf4j;
import org.checkerframework.checker.nullness.qual.NonNull;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* @author baijun
* @date: 2021/5/26
* @description: 用户表缓存
*/
@Slf4j
public class UserCache implements ICacheManager<UserCaffeine>{
private UserCaffeineMapper mapper;
private LoadingCache<String, UserCaffeine> loadingCache;
public UserCache(UserCaffeineMapper mapper) {
this.mapper = mapper;
loadingCache = Caffeine.newBuilder()
//缓存写入/删除监控
.writer(new CacheWriter<String, UserCaffeine>() {
@Override
public void write(@NonNull String key, @NonNull UserCaffeine value) { //此方法是同步阻塞的
String sb = "UserCache写入用户信息 api: "+key;
log.info(sb);
}
@Override
public void delete(@NonNull String key, UserCaffeine value, @NonNull RemovalCause cause) {
String sb = "UserCache删除用户信息 api: "+key;
log.info(sb);
}
})
//TODO 扩展不存在的值查询 redis
.build((String key) -> null);
this.initCache();
}
private void initCache(){
List<UserCaffeine> userCaffeineList = mapper.selectList(new QueryWrapper<UserCaffeine>().select("id","userid","systemid","serviceid","servicename"));
Map<String,UserCaffeine> map = new HashMap<>();
for (UserCaffeine userCaffeine : userCaffeineList) {
String key = userCaffeine.getId();
map.put(key,userCaffeine);
}
this.loadingCache.putAll(map);
}
/**
* 刷新缓存
*/
public void refresh(){
this.loadingCache.invalidateAll();
this.initCache();
}
@Override
public UserCaffeine get(String key) {
return this.loadingCache.get(key);
}
@Override
public void put(String key, UserCaffeine value) {
this.loadingCache.put(key, value);
}
@Override
public void del(String key) {
this.loadingCache.invalidate(key);
}
@Override
public void refresh(Map<String, UserCaffeine> payLoad) {
this.loadingCache.invalidateAll();
this.loadingCache.putAll(payLoad);
}
@Override
public LoadingCache<String, UserCaffeine> getCache() {
return this.loadingCache;
}
}
缓存配置类
package com.jx.bas.console.config;
import com.jx.bas.console.cache.RegionCache;
import com.jx.bas.console.cache.UserCache;
import com.jx.bas.console.modules.zy.dao.RegionCaffeineMapper;
import com.jx.bas.console.modules.zy.dao.UserCaffeineMapper;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
/**
* @author baijun
* @date: 2021/5/26
* @description: 缓存配置
*/
@Configuration
public class CacheConfig {
/**
* @return 用户 缓存
*/
@Bean
public UserCache userCache(UserCaffeineMapper userCaffeineMapper){
return new UserCache(userCaffeineMapper);
}
/**
* @return 地区 缓存
*/
@Bean
public RegionCache regionCache(RegionCaffeineMapper regionCaffeineMapper){
return new RegionCache(regionCaffeineMapper);
}
}
这里在控制层演示,操作缓存数据
@Resource
UserCache userCache;
@Resource
RegionCache regionCache;
@ApiOperation(value = "查询全部缓存")
@GetMapping("/userCaffeine")
public Map<String,UserCaffeine> userCaffeine(){
ConcurrentMap<String,UserCaffeine> map =userCache.getCache().asMap();
return map;
}
@ApiOperation(value = "根据map的k查询缓存")
@GetMapping("/userCaffeine2")
public UserCaffeine userCaffeine2(){
UserCaffeine userCaffeine =userCache.get("40288a356c564ca3016c564eab560079");
return userCaffeine;
}
@ApiOperation(value = "根据map的k迭代缓存数据")
@GetMapping("/userCaffeine3")
public String userCaffeine3(String userId,String xtid,String fwid){
String serviceName = null;
ConcurrentMap<String, UserCaffeine> userMap =userCache.getCache().asMap();
Iterator iterator =userMap.keySet().iterator();
while (iterator.hasNext()){
Object key = iterator.next();
if (userMap.get(key).getUserid().equals(userId) && userMap.get(key).getSystemid().equals(xtid) && userMap.get(key).getServiceid().equals(fwid)){
serviceName = userMap.get(key).getServicename();
}
}
return serviceName;
}
定时器刷新缓存
package com.jx.bas.console.cache;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* @author baijun
* @date: 2021/6/2
* @description: 定时器刷新缓存
*/
@Component
@Slf4j
public class Jobs {
@Resource
UserCache userCache;
@Resource
RegionCache regionCache;
//间隔30秒刷新
@Scheduled(fixedRate = 30000)
public void fixedRateCaffeine() {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日-hh时mm分ss秒");
userCache.refresh();
log.info("定时器:"+sdf.format(new Date())+"刷新用户信息缓存");
regionCache.refresh();
log.info("定时器:"+sdf.format(new Date())+"刷新地区信息缓存");
}
}