package com.mzl.flower.service.impl.district;
import cn.hutool.core.util.IdUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.mzl.flower.base.cache.StringCacheClient;
import com.mzl.flower.config.exception.ValidationException;
import com.mzl.flower.config.security.SecurityUtils;
import com.mzl.flower.dto.map.tengxun.TengxunDistrict;
import com.mzl.flower.dto.request.district.CreateDistrictTengxunDTO;
import com.mzl.flower.dto.response.district.DistrictTengxunVO;
import com.mzl.flower.dto.response.system.AreaAppDTO;
import com.mzl.flower.dto.response.system.AreaAppTmpDTO;
import com.mzl.flower.dto.response.system.AreaDTO;
import com.mzl.flower.entity.district.DistrictTengxunDO;
import com.mzl.flower.entity.district.DistrictTengxunDO;
import com.mzl.flower.mapper.district.DistrictTengxunMapper;
import com.mzl.flower.mapper.district.DistrictTengxunMapperCustom;
import com.mzl.flower.service.district.DistrictTengxunService;
import com.mzl.flower.utils.ConverterUtil;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.Optional;
import java.util.stream.Collectors;
/**
*
* 对接高德地图行政区划 服务实现类
*
*
* @author @TaoJie
* @since 2024-12-19
*/
@Service
public class DistrictTengxunServiceImpl extends ServiceImpl implements DistrictTengxunService {
@Autowired
private DistrictTengxunMapperCustom districtTengxunMapperCustom;
@Override
public void removeAllDistricts() {
districtTengxunMapperCustom.removeAllDistricts();
}
@Autowired
private StringCacheClient stringCacheClient;
@Autowired
private Gson gson;
@Override
public void refreshDistrict() {
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
// 遍历根节点,构建每棵树形结构
List areaDTOList = new ArrayList<>();
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
// 将树形转换成前端需要的结构
AreaDTO areaDTO = transform(rootNode);
areaDTOList.add(areaDTO);
// 打印每个根节点对应的树形 JSON
Gson gson = new Gson();
System.out.println("根节点:" + rootNode.getName());
System.out.println("树形结构 JSON:" + gson.toJson(areaDTO));
}
// 如果需要整个树形结构的 JSON
Gson gson = new Gson();
System.out.println("整个中国地图的 JSON:" + gson.toJson(areaDTOList));
}
}
// 递归构建树形结构
private static void buildTree(DistrictTengxunVO parent, List allNodes) {
List children = allNodes.stream()
.filter(node -> parent.getId().equals(node.getParentId()))
.collect(Collectors.toList());
parent.setChildren(children);
for (DistrictTengxunVO child : children) {
buildTree(child, allNodes);
}
}
// 转换方法
public static AreaDTO transform(DistrictTengxunVO sourceNode) {
if (sourceNode == null) {
return null;
}
// 映射当前节点
AreaDTO targetNode = new AreaDTO(sourceNode.getCode(), sourceNode.getName());
// 递归映射子节点
if (sourceNode.getChildren() != null) {
for (DistrictTengxunVO child : sourceNode.getChildren()) {
targetNode.getChildren().add(transform(child));
}
}
return targetNode;
}
public static AreaDTO transformCodeEqName(DistrictTengxunVO sourceNode) {
if (sourceNode == null) {
return null;
}
// 映射当前节点
AreaDTO targetNode = new AreaDTO(sourceNode.getName(), sourceNode.getName());
// 递归映射子节点
if (sourceNode.getChildren() != null) {
for (DistrictTengxunVO child : sourceNode.getChildren()) {
targetNode.getChildren().add(transformCodeEqName(child));
}
}
return targetNode;
}
public static AreaAppTmpDTO transformApp(DistrictTengxunVO sourceNode,int level) {
if (sourceNode == null) {
return null;
}
// 映射当前节点
AreaAppTmpDTO targetNode = new AreaAppTmpDTO(sourceNode.getId(), level+"", sourceNode.getName(), sourceNode.getParentId());
// 递归映射子节点
if (sourceNode.getChildren() != null) {
for (DistrictTengxunVO child : sourceNode.getChildren()) {
targetNode.getChildren().add(transformApp(child,level++));
}
}
return targetNode;
}
public static AreaAppDTO transformApp2(DistrictTengxunVO sourceNode) {
if (sourceNode == null) {
return null;
}
// 映射当前节点
AreaAppDTO targetNode = new AreaAppDTO(sourceNode.getCode(), sourceNode.getName());
// 递归映射子节点
if (sourceNode.getChildren() != null) {
for (DistrictTengxunVO child : sourceNode.getChildren()) {
targetNode.getChildren().add(transformApp2(child));
}
}
return targetNode;
}
@Override
public List getAllDistrict() {
return baseMapper.selectList(new LambdaQueryWrapper().eq(DistrictTengxunDO::getDeleted, false).orderByAsc(DistrictTengxunDO::getCode));
}
@Override
public List getAreaDTOListByDB() {
return null;
}
@Override
public List getAreaDTOListByJsonFile() {
return null;
}
@Override
public void saveRemoteDistricts(List districtTengxunDOList) {
districtTengxunDOList.stream().forEach(districtTengxunDO -> {
// 保存数据库中必要的信息
districtTengxunDO.create();
districtTengxunDO.setCreateBy("system");
districtTengxunDO.setUpdateBy("system");
});
saveOrUpdateBatch(districtTengxunDOList);
/*
List existList=new ArrayList<>();
List noneExistList=new ArrayList<>();
// 查看是否已经存在code,如果存在则更新,不存在则插入
districtTengxunDOList.stream().forEach(districtTengxunDO -> {
List list = list(new LambdaQueryWrapper().eq(DistrictTengxunDO::getDeleted, false).eq(DistrictTengxunDO::getCode,districtTengxunDO.getCode() ));
if (CollectionUtils.isNotEmpty(list)) {
existList.add(districtTengxunDO);
} else {
// 插入
noneExistList.add(districtTengxunDO);
}
});
removeAllDistricts();
System.out.println("删除成功");
// 保存数据入库
saveBatch(districtTengxunDOList);*/
System.out.println("保存成功");
}
@Override
public List getDistrictTreeList() {
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
}
return roots;
}
return null;
}
@Transactional
@Override
public boolean createDistrict(CreateDistrictTengxunDTO dto) {
// 查看编码是否存在
if (count(new LambdaQueryWrapper()
.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getCode, dto.getCode()))>0) {
throw new ValidationException("当前编码已经存在,code全局唯一");
}
// 查看相同节点下的名称是否存在,这里的partentId可能是null的情况
if(StringUtils.isNotBlank(dto.getName())){
LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getName, dto.getName());
if (dto.getParentId() == null) {
queryWrapper.isNull(DistrictTengxunDO::getParentId);
} else {
queryWrapper.eq(DistrictTengxunDO::getParentId, dto.getParentId());
}
if (count(queryWrapper)>0) {
throw new ValidationException("当前名称已经存在");
}
}
if(StringUtils.isNotBlank(dto.getFullname())){
LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getFullname, dto.getFullname());
if (dto.getParentId() == null) {
queryWrapper.isNull(DistrictTengxunDO::getParentId);
} else {
queryWrapper.eq(DistrictTengxunDO::getParentId, dto.getParentId());
}
if (count(queryWrapper)>0) {
throw new ValidationException("当前全称已经存在");
}
}
DistrictTengxunDO districtTengxunDO =new DistrictTengxunDO();
BeanUtils.copyProperties(dto,districtTengxunDO);
districtTengxunDO.setId(IdUtil.simpleUUID());
districtTengxunDO.create(SecurityUtils.getUserId());
// 保存
boolean result=save(districtTengxunDO);
// 清空缓存
clearChineseDataCache();
return result;
}
@Transactional
@Override
public boolean deleteDistrict(String id) {
DistrictTengxunDO existsDistrict = getById(id);
existsDistrict.update(SecurityUtils.getUserId());
existsDistrict.setDeleted(true);
updateById(existsDistrict);
List childrenList = list(new LambdaQueryWrapper().eq(DistrictTengxunDO::getParentId, id));
if(CollectionUtils.isNotEmpty(childrenList)){
childrenList.stream().forEach(districtTengxunDO -> {
deleteDistrict(districtTengxunDO.getId());
});
}
// 清空缓存
clearChineseDataCache();
return true;
}
@Transactional
@Override
public boolean updateDistrict(CreateDistrictTengxunDTO dto) {
DistrictTengxunDO existsDistrict = getById(dto.getId());
if(Objects.isNull(existsDistrict)){
throw new ValidationException("当前id不存在");
}
// 查看编码是否存在
if (count(new LambdaQueryWrapper()
.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getCode, dto.getCode()).ne(DistrictTengxunDO::getId,dto.getId()))>0) {
throw new ValidationException("当前编码已经存在,code全局唯一");
}
// 查看相同节点下的名称是否存在,这里的partentId可能是null的情况
if(StringUtils.isNotBlank(dto.getName())){
LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getName, dto.getName())
.ne(DistrictTengxunDO::getId,dto.getId());
if (dto.getParentId() == null) {
queryWrapper.isNull(DistrictTengxunDO::getParentId);
} else {
queryWrapper.eq(DistrictTengxunDO::getParentId, dto.getParentId());
}
if (count(queryWrapper)>0) {
throw new ValidationException("当前名称已经存在");
}
}
if(StringUtils.isNotBlank(dto.getFullname())){
LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(DistrictTengxunDO::getDeleted, false)
.eq(DistrictTengxunDO::getFullname, dto.getFullname())
.ne(DistrictTengxunDO::getId,dto.getId());
if (dto.getParentId() == null) {
queryWrapper.isNull(DistrictTengxunDO::getParentId);
} else {
queryWrapper.eq(DistrictTengxunDO::getParentId, dto.getParentId());
}
if (count(queryWrapper)>0) {
throw new ValidationException("当前全称已经存在");
}
}
BeanUtils.copyProperties(dto, existsDistrict);
existsDistrict.update(SecurityUtils.getUserId());
boolean result= updateById(existsDistrict);
// 清空缓存
clearChineseDataCache();
return result;
}
@Override
public String getChineseArea() {
String result = stringCacheClient.get("CHINA_AREA_DATA");
if (StringUtils.isNotBlank(result)) {
return result;
} else {
// 打印每个根节点对应的树形 JSON
Gson gson = new Gson();
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
// 遍历根节点,构建每棵树形结构
List areaDTOList = new ArrayList<>();
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
// 将树形转换成前端需要的结构
AreaDTO areaDTO = transform(rootNode);
areaDTOList.add(areaDTO);
}
result=gson.toJson(areaDTOList);
if(StringUtils.isNotBlank(result)){
stringCacheClient.set("CHINA_AREA_DATA", result);
}
return result;
}
return "";
}
}
@Override
public void clearChineseDataCache() {
stringCacheClient.delete("CHINA_AREA_DATA");
stringCacheClient.delete("CHINA_AREA_DATA_APP");
stringCacheClient.delete("CHINA_AREA_DATA_WEB");
}
@Override
public String getChineseAreaForApp() {
String result = stringCacheClient.get("CHINA_AREA_DATA_APP");
if (StringUtils.isNotBlank(result)) {
return result;
} else {
// 打印每个根节点对应的树形 JSON
Gson gson = new Gson();
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
// 遍历根节点,构建每棵树形结构
List areaDTOList = new ArrayList<>();
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
// 将树形转换成前端需要的结构
AreaAppTmpDTO areaDTO = transformApp(rootNode,1);
areaDTOList.add(areaDTO);
}
result=gson.toJson(areaDTOList);
if(StringUtils.isNotBlank(result)){
stringCacheClient.set("CHINA_AREA_DATA_APP", result);
}
return result;
}
return "";
}
}
@Override
public String getChineseAreaForWeb() {
String result = stringCacheClient.get("CHINA_AREA_DATA_WEB");
if (StringUtils.isNotBlank(result)) {
return result;
} else {
// 打印每个根节点对应的树形 JSON
Gson gson = new Gson();
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
// 遍历根节点,构建每棵树形结构
List areaDTOList = new ArrayList<>();
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
// 将树形转换成前端需要的结构
AreaDTO areaDTO = transformCodeEqName(rootNode);
areaDTOList.add(areaDTO);
}
List formatterDistrict =normalizeTreeToThreeLevels(areaDTOList);
// result=gson.toJson(areaDTOList);
result=gson.toJson(formatterDistrict);
if(StringUtils.isNotBlank(result)){
stringCacheClient.set("CHINA_AREA_DATA_WEB", result);
}
return result;
}
return "";
}
}
public static List normalizeTreeToThreeLevels(List tree) {
List result = new ArrayList<>();
for (AreaDTO node : tree) {
int depth = getTreeDepth(node);
if(depth<3){
List childrenList=new ArrayList<>();
childrenList.add(node);
AreaDTO tengxunDistrict= new AreaDTO();
BeanUtils.copyProperties(node, tengxunDistrict);
tengxunDistrict.setChildren(childrenList);
// 虚拟的id、code
tengxunDistrict.setCode(tengxunDistrict.getCode());
result.add(tengxunDistrict);
continue;
}else{
result.add(node);
}
}
return result;
}
private static int getTreeDepth(AreaDTO node) {
if (node == null || node.getChildren() == null || node.getChildren().isEmpty()) {
return 1;
}
int maxDepth = 0;
for (AreaDTO child : node.getChildren()) {
maxDepth = Math.max(maxDepth, getTreeDepth(child));
}
return maxDepth + 1;
}
public String getChineseAreaForApp2() {
String result = stringCacheClient.get("CHINA_AREA_DATA_APP");
if (StringUtils.isNotBlank(result)) {
return result;
} else {
// 打印每个根节点对应的树形 JSON
Gson gson = new Gson();
List districtTengxunDOList = getAllDistrict();
List districtTengxunVOList = ConverterUtil.transList(districtTengxunDOList, DistrictTengxunVO.class);
if (CollectionUtils.isNotEmpty(districtTengxunDOList)) {
// 找出所有 parent_id 为 null 的节点作为根节点集合
List roots = districtTengxunVOList.stream()
.filter(districtTengxunVO -> districtTengxunVO.getParentId() == null)
.collect(Collectors.toList());
// 遍历根节点,构建每棵树形结构
List areaDTOList = new ArrayList<>();
for (DistrictTengxunVO rootNode : roots) {
// 构建树形结构
buildTree(rootNode, districtTengxunVOList);
// 将树形转换成前端需要的结构
AreaAppDTO areaDTO = transformApp2(rootNode);
areaDTOList.add(areaDTO);
}
result=gson.toJson(areaDTOList);
if(StringUtils.isNotBlank(result)){
stringCacheClient.set("CHINA_AREA_DATA_APP", result);
}
return result;
}
return "";
}
}
}