![JAR search and dependency download from the Maven repository](/logo.png)
com.wudgaby.starter.dict.load.DefaultDictCacheImpl Maven / Gradle / Ivy
package com.wudgaby.starter.dict.load;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.lang.tree.Tree;
import cn.hutool.core.lang.tree.TreeUtil;
import cn.hutool.core.util.StrUtil;
import com.github.benmanes.caffeine.cache.Cache;
import com.github.benmanes.caffeine.cache.Caffeine;
import com.google.common.collect.Lists;
import com.wudgaby.starter.dict.api.DictCachedApi;
import com.wudgaby.starter.dict.api.DictVO;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.context.event.ApplicationReadyEvent;
import org.springframework.context.event.EventListener;
import org.springframework.scheduling.annotation.Scheduled;
import java.util.*;
import java.util.stream.Collectors;
/**
* @author : wudgaby
* @version : 1.0.0
* @date : 2023/11/2 0002 17:23
* @desc :
*/
@Slf4j
@RequiredArgsConstructor
public class DefaultDictCacheImpl implements DictCache {
private final int REFRESH_DELAY = 60 * 1000;
private final Cache DICT_TYPE_CACHED = Caffeine.newBuilder()
.maximumSize(10_000)
.build();
private final Cache> DICT_ITEM_CACHED = Caffeine.newBuilder()
.maximumSize(10_000)
.build();
private final DictCachedApi dictCachedApi;
/**
* 最后更新时间
*/
private volatile Date lastUpdatedTimeForDictType;
private volatile Date lastUpdatedTimeForDictItem;
@Override
@EventListener(ApplicationReadyEvent.class)
public void init2Cached() {
log.info("初始化字典, 缓存至内存");
load();
}
@Override
@Scheduled(initialDelay = REFRESH_DELAY, fixedDelay = REFRESH_DELAY)
public void refresh() {
log.info("刷新字典缓存");
load();
}
@Override
public List listDictTypes() {
return Lists.newArrayList(DICT_TYPE_CACHED.asMap().values());
}
@Override
public List listDictItems() {
List allItems = Lists.newArrayList();
DICT_ITEM_CACHED.asMap().values().forEach(allItems::addAll);
return allItems;
}
@Override
public Optional getDictItemByVal(String type, String value) {
List dictDTOList = DICT_ITEM_CACHED.getIfPresent(type);
if(CollectionUtil.isEmpty(dictDTOList)) {
return Optional.empty();
}
return dictDTOList.stream().filter(dictDTO -> StrUtil.equals(dictDTO.getValue(), value)).findFirst();
}
@Override
public Optional getDictItemByLabel(String type, String label) {
List dictDTOList = DICT_ITEM_CACHED.getIfPresent(type);
if(CollectionUtil.isEmpty(dictDTOList)) {
return Optional.empty();
}
return dictDTOList.stream().filter(dictDTO -> StrUtil.equals(dictDTO.getLabel(), label)).findFirst();
}
@Override
public List listDictItemsByType(String type) {
return DICT_ITEM_CACHED.getIfPresent(type);
}
@Override
public List> treeDictItemsByType(String type) {
List listDictItems = this.listDictItemsByType(type);
if(CollectionUtil.isEmpty(listDictItems)) {
return Lists.newArrayList();
}
//TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
// 最大递归深度
//treeNodeConfig.setDeep(3);
return TreeUtil.build(listDictItems, 0L,
(treeNode, tree) -> {
tree.setId(treeNode.getId());
tree.setParentId(treeNode.getPid());
tree.setWeight(treeNode.getSort());
tree.setName(treeNode.getLabel());
// 扩展属性 ...
tree.putExtra("dictType", treeNode.getDictType());
tree.putExtra("dictValue", treeNode.getValue());
});
}
private void load(){
List sysDictTypeList = null;
List sysDictItemList = null;
if(lastUpdatedTimeForDictType == null || lastUpdatedTimeForDictItem == null) {
sysDictTypeList = dictCachedApi.listDictTypes();
sysDictItemList = dictCachedApi.listDictItems();
} else {
boolean hasUpdateType = dictCachedApi.hasUpdateForType(lastUpdatedTimeForDictType);
if(hasUpdateType){
log.info("字典类型有更新");
sysDictTypeList = dictCachedApi.listDictTypes();
}
boolean hasUpdateForItem = dictCachedApi.hasUpdateForItem(lastUpdatedTimeForDictItem);
if(hasUpdateForItem){
log.info("字典项有更新");
sysDictItemList = dictCachedApi.listDictItems();
}
}
if(CollectionUtil.isNotEmpty(sysDictTypeList)){
// 字典类型
Map dictTypeMap = sysDictTypeList.stream().collect(Collectors.toMap(DictVO::getDictType, dict -> dict));
DICT_TYPE_CACHED.invalidateAll();
DICT_TYPE_CACHED.putAll(dictTypeMap);
lastUpdatedTimeForDictType = sysDictTypeList.stream().filter(s -> Objects.nonNull(s.getUpdateTime()))
.max(Comparator.comparing(DictVO::getUpdateTime))
.map(DictVO::getUpdateTime)
.orElse(new Date());
}
if(CollectionUtil.isNotEmpty(sysDictItemList)){
// 字典类型分组
Map> dictItemMap = sysDictItemList.stream().collect(Collectors.groupingBy(DictVO::getDictType));
DICT_ITEM_CACHED.invalidateAll();
DICT_ITEM_CACHED.putAll(dictItemMap);
lastUpdatedTimeForDictItem = sysDictItemList.stream().filter(s -> Objects.nonNull(s.getUpdateTime()))
.max(Comparator.comparing(DictVO::getUpdateTime))
.map(DictVO::getUpdateTime)
.orElse(new Date());
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy