/**
 * Copyright 2019 DH
 * All right reserved.
 * 项目名称: 大恒泰山系统
 * 创建日期:2022/8/22
 */
package org.springblade.modules.baseinfo.region.controller;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
import io.swagger.annotations.*;
import lombok.AllArgsConstructor;
import org.springblade.constant.BusinessConstant;
import org.springblade.core.boot.ctrl.BladeController;
import org.springblade.core.mp.support.Condition;
import org.springblade.core.secure.BladeUser;
import org.springblade.core.secure.utils.AuthUtil;
import org.springblade.core.tool.api.R;
import org.springblade.core.tool.utils.Func;
import org.springblade.etl.entity.EtlAdCdEntity;
import org.springblade.etl.service.IEtlAdCdService;
import org.springblade.modules.baseinfo.org.entity.DeptRegionEntity;
import org.springblade.modules.baseinfo.org.service.IDeptRegionService;
import org.springblade.modules.baseinfo.region.dto.RegionInfoDTO;
import org.springblade.modules.baseinfo.region.entity.OrgRegionInfoEntity;
import org.springblade.modules.baseinfo.region.entity.RegionInfoEntity;
import org.springblade.modules.baseinfo.region.entity.RegionTreeNodeEntity;
import org.springblade.modules.baseinfo.region.service.IBaseInfoRegionService;
import org.springblade.modules.baseinfo.region.service.IOrgRegionInfoService;
import org.springblade.modules.baseinfo.region.vo.RegionInfoVO;
import org.springblade.modules.baseinfo.region.wrapper.RegionInfoWrapper;
import org.springblade.modules.system.service.IDeptService;
import org.springblade.modules.system.service.IRegionService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.web.bind.annotation.*;
import springfox.documentation.annotations.ApiIgnore;

import java.util.LinkedList;
import java.util.List;


/***
 * Date:2022/8/22
 * Title:行政区划管理
 * Description：对本文件的详细描述，原则上不能少于30字
 * @author dylan
 * @version 1.0
 * Remark：认为有必要的其他信息
 */
@RestController
@RequestMapping("galaxy-business/baseinfo/region")
@AllArgsConstructor
@Api(value = "行政区划管理", tags = "行政区划管理")
public class BaseInfoRegionController extends BladeController {
	private final IBaseInfoRegionService baseInfoRegionService;
	private final IDeptService deptService;
	private final IRegionService regionService;
	private final IEtlAdCdService etlAdCdService;
	private final IOrgRegionInfoService iOrgRegionInfoService;
	private final IDeptRegionService deptRegionService;

	@Autowired
	private RedisTemplate redisTemplate;



	@GetMapping("/children/list")
	@ApiOperationSupport(order = 1)
	@ApiOperation(value = "分页")
	public R<List<RegionInfoEntity>> childrenList() {
		BladeUser user = AuthUtil.getUser();
		if (BusinessConstant.ROLE_SYS_ADMIN.equals(user.getRoleName())) {
			LambdaQueryWrapper<RegionInfoEntity> wrapper = Wrappers.<RegionInfoEntity>query().lambda();
			wrapper.eq(RegionInfoEntity::getIsDeleted, 0);
			wrapper.eq(RegionInfoEntity::getParentCode, BusinessConstant.REGION_NM_ADCODE);
			List<RegionInfoEntity> list = baseInfoRegionService.list(wrapper);
			return R.data(list);
		} else if (BusinessConstant.ROLE_ORG_ADMIN.equals(user.getRoleName()) || BusinessConstant.ROLE_COMPANY_ADMIN.equals(user.getRoleName())) {
			LambdaQueryWrapper<DeptRegionEntity> deptRegionEntityLambdaQueryWrapper = Wrappers.<DeptRegionEntity>query().lambda();
			deptRegionEntityLambdaQueryWrapper.eq(DeptRegionEntity::getIsDeleted, 0);
			deptRegionEntityLambdaQueryWrapper.eq(DeptRegionEntity::getDeptId, Func.toLong(user.getDeptId()));
			DeptRegionEntity deptRegionEntity = deptRegionService.getOne(deptRegionEntityLambdaQueryWrapper);
			LambdaQueryWrapper<RegionInfoEntity> regionInfoEntityLambdaQueryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
			regionInfoEntityLambdaQueryWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
			regionInfoEntityLambdaQueryWrapper.eq(RegionInfoEntity::getParentCode, deptRegionEntity.getAdcd());
			List<RegionInfoEntity> list = baseInfoRegionService.list(regionInfoEntityLambdaQueryWrapper);
			return R.data(list);
		}
		return R.data(null);
	}

	@GetMapping("/lazy-tree")
	@ApiImplicitParams({
		@ApiImplicitParam(name = "adcd", value = "行政区划代码", paramType = "query", dataType = "string"),
	})
	@ApiOperationSupport(order = 2)
	@ApiOperation(value = "树")
	public R<List<RegionTreeNodeEntity>> lazyTree(@ApiIgnore OrgRegionInfoEntity orgRegionInfoEntity) {
		List<RegionTreeNodeEntity> nodeEntities = new LinkedList<>();
		BladeUser user = AuthUtil.getUser();
		if (BusinessConstant.ROLE_COMPANY_ADMIN.equals(user.getRoleName()) || BusinessConstant.ROLE_COMPANY_SERVICE_PERSON.equals(user.getRoleName())) {
			LambdaQueryWrapper<OrgRegionInfoEntity> queryWrapper = Wrappers.<OrgRegionInfoEntity>query().lambda();
			if (orgRegionInfoEntity.getAdcd() != null) {
				queryWrapper.eq(OrgRegionInfoEntity::getParentCode, orgRegionInfoEntity.getAdcd());
			} else {
				queryWrapper.eq(OrgRegionInfoEntity::getParentCode, BusinessConstant.REGION_NM_ADCODE);
			}
			queryWrapper.eq(OrgRegionInfoEntity::getDeptId, Func.toLong(user.getDeptId()));
			queryWrapper.eq(OrgRegionInfoEntity::getRegionActive, 1);
			List<OrgRegionInfoEntity> list = iOrgRegionInfoService.list(queryWrapper);
			for (OrgRegionInfoEntity entity : list) {
				if (entity.getRtuCount() > 0) {
					RegionTreeNodeEntity nodeEntity = new RegionTreeNodeEntity();
					nodeEntity.setId(entity.getAdcd());
					nodeEntity.setValue(entity.getAdcd());
					nodeEntity.setTitle(entity.getAdnm());
					nodeEntity.setKey(entity.getAdcd());
					nodeEntity.setParentId(entity.getParentCode());

					nodeEntities.add(nodeEntity);
				}
			}
		} else {
			LambdaQueryWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
			if (orgRegionInfoEntity.getAdcd() != null) {
				queryWrapper.eq(RegionInfoEntity::getParentCode, orgRegionInfoEntity.getAdcd());
			} else {
				queryWrapper.eq(RegionInfoEntity::getParentCode, BusinessConstant.REGION_NM_ADCODE);
			}
			List<RegionInfoEntity> list = baseInfoRegionService.list(queryWrapper);
			for (RegionInfoEntity entity : list) {
				RegionTreeNodeEntity nodeEntity = new RegionTreeNodeEntity();
				nodeEntity.setId(entity.getAdcd());
				nodeEntity.setValue(entity.getAdcd());
				nodeEntity.setTitle(entity.getAdnm());
				nodeEntity.setKey(entity.getAdcd());
				nodeEntity.setParentId(entity.getParentCode());
				nodeEntities.add(nodeEntity);
			}
		}
		return R.data(nodeEntities);
	}

	@GetMapping("/tree")
	@ApiOperationSupport(order = 2)
	@ApiOperation(value = "树")
	public R<List<RegionTreeNodeEntity>> regionTree() {
		ValueOperations<String, String> opsHash = redisTemplate.opsForValue();
		List<RegionTreeNodeEntity> nodeEntities = new LinkedList<>();
		BladeUser user = AuthUtil.getUser();
		if (BusinessConstant.ROLE_SYS_ADMIN.equals(user.getRoleName())) {
			String regionJson = opsHash.get("region.admin");
			if (null != regionJson) {
				nodeEntities = JSON.parseObject(regionJson, new TypeReference<List<RegionTreeNodeEntity>>() {
				});
			} else {
				LambdaQueryWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
				queryWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
				queryWrapper.eq(RegionInfoEntity::getParentCode, BusinessConstant.REGION_ROOT_ADCODE);
				List<RegionInfoEntity> list = baseInfoRegionService.list(queryWrapper);
				for (RegionInfoEntity entity : list) {
					RegionTreeNodeEntity nodeEntity = new RegionTreeNodeEntity();
					nodeEntity.setId(entity.getAdcd());
					nodeEntity.setValue(entity.getAdcd());
					nodeEntity.setTitle(entity.getAdnm());
					nodeEntity.setText(entity.getAdnm());
					nodeEntity.setKey(entity.getAdcd());
					nodeEntity.setParentId(entity.getParentCode());
					getChildren(nodeEntity, entity);
					if (nodeEntity.getChildren() != null && nodeEntity.getChildren().size() > 0) {
						nodeEntity.setHasChildren(true);
					} else {
						nodeEntity.setHasChildren(false);
					}
					nodeEntities.add(nodeEntity);
				}
				opsHash.set("region.admin", JSON.toJSONString(nodeEntities));
			}
		} else {
			String regionJson = opsHash.get("region." + user.getDeptId());
			if (null != regionJson) {
				nodeEntities = JSON.parseObject(regionJson, new TypeReference<List<RegionTreeNodeEntity>>() {
				});
			} else {
				LambdaQueryWrapper<DeptRegionEntity> deptRegionEntityLambdaQueryWrapper = Wrappers.<DeptRegionEntity>query().lambda();
				deptRegionEntityLambdaQueryWrapper.eq(DeptRegionEntity::getIsDeleted, 0);
				deptRegionEntityLambdaQueryWrapper.eq(DeptRegionEntity::getDeptId, Func.toLong(user.getDeptId()));
				DeptRegionEntity deptRegionEntity = deptRegionService.getOne(deptRegionEntityLambdaQueryWrapper);
				LambdaQueryWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
				queryWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
				if (null == deptRegionEntity){
					queryWrapper.eq(RegionInfoEntity::getAdcd, BusinessConstant.REGION_NM_ADCODE);
				}else{
					queryWrapper.eq(RegionInfoEntity::getAdcd, deptRegionEntity.getAdcd());
				}
				List<RegionInfoEntity> list = baseInfoRegionService.list(queryWrapper);
				for (RegionInfoEntity entity : list) {
					RegionTreeNodeEntity nodeEntity = new RegionTreeNodeEntity();
					nodeEntity.setId(entity.getAdcd());
					nodeEntity.setValue(entity.getAdcd());
					nodeEntity.setTitle(entity.getAdnm());
					nodeEntity.setText(entity.getAdnm());
					nodeEntity.setKey(entity.getAdcd());
					nodeEntity.setParentId(entity.getParentCode());
					getChildren(nodeEntity, entity);
					if (nodeEntity.getChildren() != null && nodeEntity.getChildren().size() > 0) {
						nodeEntity.setHasChildren(true);
					} else {
						nodeEntity.setHasChildren(false);
					}
					nodeEntities.add(nodeEntity);
				}
				opsHash.set("region." + user.getDeptId(), JSON.toJSONString(nodeEntities));
			}
		}
		return R.data(nodeEntities);
	}


	private boolean getChildren(RegionTreeNodeEntity nodeEntity, OrgRegionInfoEntity regionInfoEntity) {
		LambdaQueryWrapper<OrgRegionInfoEntity> queryWrapper = Wrappers.<OrgRegionInfoEntity>query().lambda();
		queryWrapper.eq(OrgRegionInfoEntity::getParentCode, regionInfoEntity.getAdcd());
		queryWrapper.eq(OrgRegionInfoEntity::getDeptId, regionInfoEntity.getDeptId());
		queryWrapper.eq(OrgRegionInfoEntity::getRegionActive, 1);
		List<OrgRegionInfoEntity> list = iOrgRegionInfoService.list(queryWrapper);
		if (null != list && list.size() > 0) {
			List<RegionTreeNodeEntity> nodeEntities = new LinkedList<>();
			for (OrgRegionInfoEntity entity : list) {
				if (entity.getRtuCount() > 0) {
					RegionTreeNodeEntity node = new RegionTreeNodeEntity();
					node.setId(entity.getAdcd());
					node.setValue(entity.getAdcd());
					node.setTitle(entity.getAdnm());
					node.setText(entity.getAdnm());
					node.setKey(entity.getAdcd());
					node.setParentId(entity.getParentCode());
					getChildren(node, entity);
					if (node.getChildren() != null && node.getChildren().size() > 0) {
						node.setHasChildren(true);
					} else {
						node.setHasChildren(false);
					}
					nodeEntities.add(node);
				}
			}
			nodeEntity.setChildren(nodeEntities);
		}
		return true;
	}

	private boolean getChildren(RegionTreeNodeEntity nodeEntity, RegionInfoEntity regionInfoEntity) {
		LambdaQueryWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
		queryWrapper.eq(RegionInfoEntity::getParentCode, regionInfoEntity.getAdcd());
		List<RegionInfoEntity> list = baseInfoRegionService.list(queryWrapper);
		if (null != list && list.size() > 0) {
			List<RegionTreeNodeEntity> nodeEntities = new LinkedList<>();
			for (RegionInfoEntity entity : list) {
				RegionTreeNodeEntity node = new RegionTreeNodeEntity();
				node.setId(entity.getAdcd());
				node.setValue(entity.getAdcd());
				node.setTitle(entity.getAdnm());
				node.setText(entity.getAdnm());
				node.setKey(entity.getAdcd());
				node.setParentId(entity.getParentCode());
				getChildren(node, entity);
				if (node.getChildren() != null && node.getChildren().size() > 0) {
					node.setHasChildren(true);
				} else {
					node.setHasChildren(false);
				}
				nodeEntities.add(node);
			}
			nodeEntity.setChildren(nodeEntities);
		}
		return true;
	}

	/**
	 * 详情
	 */
	@GetMapping("/detail")
	@ApiOperationSupport(order = 1)
	@ApiOperation(value = "详情", notes = "传入RegionInfoEntity")
	public R<RegionInfoVO> detail(RegionInfoDTO regionInfoDTO) {
		regionInfoDTO.setAdcd(regionInfoDTO.getCode());
		regionInfoDTO.setIsDeleted(0);
		RegionInfoEntity detail = baseInfoRegionService.getOne(Condition.getQueryWrapper(regionInfoDTO));
		return R.data(RegionInfoWrapper.build().entityVO(detail));
	}

	/**
	 * 新增或修改
	 */
	@PostMapping("/submit")
	@ApiOperationSupport(order = 6)
	@ApiOperation(value = "新增或修改", notes = "传入RegionInfoDTO")
	public R submit(@RequestBody RegionInfoDTO regionInfoDTO) {
		LambdaQueryWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>query().lambda();
		queryWrapper.eq(RegionInfoEntity::getAdcd, regionInfoDTO.getCode());
		queryWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
		RegionInfoEntity entity = baseInfoRegionService.getOne(queryWrapper);
		boolean status = false;
		if (entity != null) {
			entity.setAdcd(regionInfoDTO.getCode());
			entity.setAdnm(regionInfoDTO.getName());
			entity.setStatus(1);
			entity.setIsDeleted(0);
			status = baseInfoRegionService.updateById(entity);
		} else {
			entity = new RegionInfoEntity();
			entity.setAdcd(regionInfoDTO.getCode());
			entity.setAdnm(regionInfoDTO.getName());
			entity.setParentCode(regionInfoDTO.getParentCode());
			entity.setStatus(1);
			entity.setIsDeleted(0);
			entity.setAncestors(regionInfoDTO.getAncestors() + "," + regionInfoDTO.getParentCode());
			status = baseInfoRegionService.save(entity);
		}
//		dataTaskManager.deptUpdateTask();
		return R.status(status);
	}

	/**
	 * 删除
	 */
	@PostMapping("/remove")
	@ApiOperationSupport(order = 7)
	@ApiOperation(value = "逻辑删除", notes = "传入ID数组")
	public R remove(@ApiParam(value = "主键集合") @RequestParam String id) {
		LambdaUpdateWrapper<RegionInfoEntity> queryWrapper = Wrappers.<RegionInfoEntity>update().lambda();
		queryWrapper.eq(RegionInfoEntity::getAdcd, id);
		boolean temp = baseInfoRegionService.remove(queryWrapper);
//		dataTaskManager.deptUpdateTask();
		return R.status(temp);
	}

	/**
	 * 从宏图数据导入
	 */
	@PostMapping("/import")
	@ApiImplicitParams({
		@ApiImplicitParam(name = "regionLevel", value = "行政区划层级", paramType = "query", dataType = "int"),
		@ApiImplicitParam(name = "isCovered", value = "是否覆盖", paramType = "query", dataType = "int"),
	})
	@ApiOperationSupport(order = 6)
	@ApiOperation(value = "导入", notes = "传入RegionInfoDTO")
	public R importSubmit(@RequestBody RegionInfoDTO regionInfoDTO) {
		if (regionInfoDTO.getIsCovered() == 1) {
			LambdaUpdateWrapper<RegionInfoEntity> updateWrapper = Wrappers.<RegionInfoEntity>update().lambda();
			updateWrapper.ne(RegionInfoEntity::getAdcd, "00");
			updateWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
			baseInfoRegionService.remove(updateWrapper);
		}
		List<EtlAdCdEntity> list = etlAdCdService.selectList("0");
		if (null != list && list.size() == 1) {
			String code = list.get(0).getAdcd();
			LambdaQueryWrapper<RegionInfoEntity> requestWrapper = Wrappers.<RegionInfoEntity>query().lambda();
			requestWrapper.eq(RegionInfoEntity::getAdcd, code);
			requestWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
			RegionInfoEntity regionInfoEntity = baseInfoRegionService.getOne(requestWrapper);
			if (null != regionInfoEntity) {
				regionInfoEntity.setAdnm(list.get(0).getAdnm());
				baseInfoRegionService.updateById(regionInfoEntity);
			} else {
				regionInfoEntity = new RegionInfoEntity();
				regionInfoEntity.setAdcd(code);
				regionInfoEntity.setAdnm(list.get(0).getAdnm());
				regionInfoEntity.setParentCode("00");
				regionInfoEntity.setAncestors("00");
				regionInfoEntity.setStatus(1);
				regionInfoEntity.setIsDeleted(0);
				baseInfoRegionService.save(regionInfoEntity);
			}
			importAdcd(regionInfoDTO.getRegionLevel(), 2, code, "00," + code);
		}
//		dataTaskManager.deptUpdateTask();
		return R.status(true);
	}

	private boolean importAdcd(int level, int currLevel, String parentCode, String ancestors) {
		if (currLevel > level) {
			return true;
		}
		List<EtlAdCdEntity> list = etlAdCdService.selectList(parentCode);
		if (null != list && list.size() > 0) {
			for (EtlAdCdEntity adCdEntity : list) {
				LambdaQueryWrapper<RegionInfoEntity> requestWrapper = Wrappers.<RegionInfoEntity>query().lambda();
				requestWrapper.eq(RegionInfoEntity::getAdcd, adCdEntity.getAdcd());
				requestWrapper.eq(RegionInfoEntity::getIsDeleted, 0);
				RegionInfoEntity regionInfoEntity = baseInfoRegionService.getOne(requestWrapper);
				if (null != regionInfoEntity) {
					regionInfoEntity.setAdnm(adCdEntity.getAdnm());
					baseInfoRegionService.updateById(regionInfoEntity);
				} else {
					regionInfoEntity = new RegionInfoEntity();
					regionInfoEntity.setAdcd(adCdEntity.getAdcd());
					regionInfoEntity.setAdnm(adCdEntity.getAdnm());
					regionInfoEntity.setParentCode(parentCode);
					regionInfoEntity.setAncestors(ancestors);
					regionInfoEntity.setStatus(1);
					regionInfoEntity.setIsDeleted(0);
					baseInfoRegionService.save(regionInfoEntity);
				}
				importAdcd(level, currLevel + 1, adCdEntity.getAdcd(), ancestors + "," + adCdEntity.getAdcd());
			}
		}
		return true;
	}

}
