将一些不经常改动,又频繁查询的数据 做成本地缓存,可以减轻数据库的压力,也可以加快访问速度。本次使用google的guava构造本地多线程缓存。
@Service
public class TaskCache implements InitializingBean {
// 定义一天更新一次
private long cacheDays=1;
// 用来记录最后更新时间
private long lastUpdateTime = 0;
@Autowired
FetchTaskService fetchTaskService;
Cache<Long, FetchTaskCacheResponse> fetchTaskCache = null;
// 更新方法,超过一天就更新一次
public void checkUpdate() {
if (System.currentTimeMillis() > (lastUpdateTime + cacheDays * 86400000)) {
// 拉取最新的数据
reloadAllFetchTask();
}
}
public void reloadAllFetchTask() {
boolean flag = true;
// 每次拉取100条数据
int offset = 0;
int limit = 100;
while (flag) {
// 查出最新的数据
List<FetchTask> fetchTasks = fetchTaskService .fetchTaskByPage();
if (fetchTasks == null || fetchTasks.isEmpty()) {
flag = false;
} else {
//将数据中一些不常更新的字段: id,appId,appName加入缓存
//FetchTaskCacheResponse 中定义了id,appId,appName 字段
for (FetchTask fetchTask : fetchTasks) {
FetchTaskCacheResponse response = new FetchTaskCacheResponse();
//调用BeanUtils工具,将fetchTask中的字段值,复制到response中
BeanUtils.copyProperties(fetchTask, response);
if (response != null) {
//放入缓存,id是key,response类是velue
fetchTaskCache.put(fetchTask.getId(), response);
}
}
offset += fetchTasks.size();
}
}
//记录最后更新时间
this.lastUpdateTime = System.currentTimeMillis();
}
// 根据key查缓存内容的方法
public Map<Long, FetchTaskCacheResponse> findFetchTask(Long... id) {
// 先check一下是否需要更新
checkUpdate();
if (id == null || id.length <= 0) {
return new HashMap<>();
}
Map<Long, FetchTaskCacheResponse> map = new HashMap<>();
for (Long fid : id) {
FetchTaskCacheResponse fetchTask = fetchTaskCache.getIfPresent(fid);
if (fetchTask != null) {
map.put(fetchTask.getId(), fetchTask);
}
}
return map;
}
// 获取所有缓存数据的方法
public List<FetchTaskCacheResponse> getAllFetchTaskResponse() {
// 也check一下是否需要更新
checkUpdate();
return new ArrayList<>(fetchTaskCache.asMap().values());
}
@Override
public void afterPropertiesSet() throws Exception {
fetchTaskCache = CacheBuilder.newBuilder().expireAfterWrite(cacheDays, TimeUnit.DAYS).build();
}
}