wlzboy
2025-10-26 2c86a8bd60deed0dd0e044bad6fb83f75d19a332
ruoyi-system/src/main/java/com/ruoyi/system/service/impl/DepartmentSyncServiceImpl.java
New file
@@ -0,0 +1,432 @@
package com.ruoyi.system.service.impl;
import java.util.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.domain.DepartmentSyncDTO;
import com.ruoyi.system.domain.OrderClassDTO;
import com.ruoyi.system.mapper.SysDeptMapper;
import com.ruoyi.system.service.IDepartmentSyncService;
import com.ruoyi.system.service.IDepartmentSyncDataService;
import com.ruoyi.system.service.IOrderClassDataService;
/**
 * 部门同步Service业务层处理
 *
 * 职责:接收部门数据,写入 MySQL 数据库
 * 数据来源:
 * 1. 内部查询:调用 IDepartmentSyncDataService 从 SQL Server 查询
 * 2. 外部传入:接收已查询好的数据
 *
 * @author ruoyi
 * @date 2025-10-18
 */
@Service
public class DepartmentSyncServiceImpl implements IDepartmentSyncService
{
    private static final Logger log = LoggerFactory.getLogger(DepartmentSyncServiceImpl.class);
    @Autowired
    private SysDeptMapper sysDeptMapper;
    @Autowired
    private IOrderClassDataService orderClassDataService;
    /**
     * 同步分公司和部门数据(使用外部传入的数据源)
     *
     * 执行流程:
     * 1. 接收外部传入的 DepartmentSyncDTO 列表
     * 2. 写入 MySQL 数据库(sysDeptMapper 使用默认 MySQL 数据源)
     *
     * @param branchDepts 外部传入的分公司数据列表
     * @return 同步结果
     */
    @Override
    @Transactional
    public AjaxResult syncBranchDepartments(List<DepartmentSyncDTO> branchDepts,List<OrderClassDTO> serviceOrderList,List<OrderClassDTO> dispatchOrderList)
    {
        try
        {
            if (branchDepts == null || branchDepts.isEmpty())
            {
                return AjaxResult.warn("传入的部门数据为空");
            }
            log.info("开始同步 {} 条分公司数据到 MySQL 数据库...", branchDepts.size());
            // 一次性从SQL Server查询所有编码数据,避免在循环中重复查询
            // 使用Map来跟踪已创建的分公司,key为分公司名称,value为部门ID
            Map<String, Long> branchMap = new HashMap<>();
            int createdBranch = 0;
            int updatedBranch = 0;
            int createdDept = 0;
            int updatedDept = 0;
            // 处理每一条分公司数据
            for (DepartmentSyncDTO dto : branchDepts)
            {
                String fullName = dto.getDepartmentName();
                if (StringUtils.isEmpty(fullName))
                {
                    continue;
                }
                // 解析部门名称:湛江--护士 -> 分公司:湛江分公司,部门:护士
                String[] parts = fullName.split("--");
                if (parts.length != 2)
                {
                    log.warn("部门名称格式不正确,跳过: {}", fullName);
                    continue;
                }
                String branchName = parts[0].trim() + "分公司";  // 湛江 -> 湛江分公司
                String deptName = parts[1].trim();              // 护士
                // 获取或创建分公司
                Long branchDeptId = branchMap.get(branchName);
                if (branchDeptId == null)
                {
                    // 检查分公司是否已存在(通过部门名称和parent_id=100来查询)
                    SysDept existingBranch = sysDeptMapper.checkDeptNameUnique(branchName, 100L);
                    if (existingBranch != null)
                    {
                        // 分公司已存在,更新编码
                        branchDeptId = existingBranch.getDeptId();
                        branchMap.put(branchName, branchDeptId);
                        // 检查并更新编码
                        syncOrderClassCodes(existingBranch, parts[0].trim(), serviceOrderList, dispatchOrderList);
//                        existingBranch.setDepartmentId(dto.getDepartmentId());
                        sysDeptMapper.updateDept(existingBranch);
                        log.info("更新分公司编码: {}, 服务单编码: {}, 调度单编码: {}",
                            branchName, existingBranch.getServiceOrderClass(), existingBranch.getDispatchOrderClass());
                    }
                    else
                    {
                        // 创建新的分公司
                        SysDept newBranch = new SysDept();
                        newBranch.setParentId(100L);  // 父节点为若依科技(默认100)
                        newBranch.setDeptName(branchName);
                        newBranch.setAncestors("0,100");  // 祖级列表
                        newBranch.setOrderNum(branchMap.size() + 1);  // 排序
                        newBranch.setStatus("0");  // 正常状态
                        newBranch.setCreateBy("sync");
//                        newBranch.setDepartmentId(dto.getDepartmentId());
                        // 自动匹配并设置服务单和调度单编码
                        syncOrderClassCodes(newBranch, parts[0].trim(), serviceOrderList, dispatchOrderList);
                        sysDeptMapper.insertDept(newBranch);
                        branchDeptId = newBranch.getDeptId();
                        branchMap.put(branchName, branchDeptId);
                        createdBranch++;
                        log.info("创建新分公司: {}, ID: {}, 服务单编码: {}, 调度单编码: {}",
                            branchName, branchDeptId, newBranch.getServiceOrderClass(), newBranch.getDispatchOrderClass());
                    }
                }
                // 创建或更新子部门
                // 先根据departmentId查询是否已存在
                SysDept existingDept = sysDeptMapper.selectDeptByDepartmentIdAndParentId(
                    dto.getDepartmentId(), branchDeptId);
                if (existingDept != null)
                {
                    // 部门已存在,更新信息
                    existingDept.setDeptName(deptName);
                    existingDept.setUpdateBy("sync");
//                    existingDept.setDepartmentId(dto.getDepartmentId());
                    sysDeptMapper.updateDept(existingDept);
                    updatedDept++;
                    log.info("更新部门: {} -> {}", branchName, deptName);
                }
                else
                {
                    // 检查是否存在同名部门(可能之前手动创建的)
                    SysDept sameName = sysDeptMapper.checkDeptNameUnique(deptName, branchDeptId);
                    if (sameName != null)
                    {
                        // 同名部门已存在,更新其department_id
                        sameName.setDepartmentId(dto.getDepartmentId());
                        sameName.setUpdateBy("sync");
                        sysDeptMapper.updateDept(sameName);
                        updatedDept++;
                        log.info("更新已存在的同名部门: {} -> {}, departmentId: {}",
                            branchName, deptName, dto.getDepartmentId());
                    }
                    else
                    {
                        // 创建新部门
                        SysDept newDept = new SysDept();
                        newDept.setParentId(branchDeptId);
                        newDept.setDeptName(deptName);
                        newDept.setAncestors("0,100," + branchDeptId);  // 祖级列表
                        newDept.setOrderNum(1);  // 排序
                        newDept.setStatus("0");  // 正常状态
                        newDept.setDepartmentId(dto.getDepartmentId());  // 记录SQL Server中的部门ID
                        newDept.setCreateBy("sync");
                        sysDeptMapper.insertDept(newDept);
                        createdDept++;
                        log.info("创建新部门: {} -> {}, departmentId: {}",
                            branchName, deptName, dto.getDepartmentId());
                    }
                }
            }
            String message = String.format("同步完成!创建分公司: %d, 更新分公司: %d, 创建部门: %d, 更新部门: %d",
                createdBranch, updatedBranch, createdDept, updatedDept);
            log.info(message);
            Map<String, Object> result = new HashMap<>();
            result.put("createdBranch", createdBranch);
            result.put("updatedBranch", updatedBranch);
            result.put("createdDept", createdDept);
            result.put("updatedDept", updatedDept);
            result.put("totalProcessed", branchDepts.size());
            return AjaxResult.success(message, result);
        }
        catch (Exception e)
        {
            log.error("同步分公司数据失败", e);
            return AjaxResult.error("同步失败: " + e.getMessage());
        }
    }
    /**
     * 同步转运部和子部门数据(使用外部传入的数据源)
     *
     * 执行流程:
     * 1. 确保总公司(ID=101)下存在"转运部"
     * 2. 创建转运部的子部门(直接创建,无需解析"--"格式)
     * 3. 写入 MySQL 数据库(sysDeptMapper 使用默认 MySQL 数据源)
     *
     * @param transportDepts 外部传入的转运部子部门数据列表
     * @return 同步结果
     */
    @Override
    @Transactional
    public AjaxResult syncTransportDepartments(List<DepartmentSyncDTO> transportDepts)
    {
        try
        {
            if (transportDepts == null || transportDepts.isEmpty())
            {
                return AjaxResult.warn("传入的转运部子部门数据为空");
            }
            log.info("开始同步 {} 条转运部子部门数据到 MySQL 数据库...", transportDepts.size());
            // 第一步:确保总公司(ID=101)下存在"转运部"
            Long transportDeptId = null;
            // 查询总公司是否存在
            SysDept headOffice = sysDeptMapper.selectDeptById(101L);
            if (headOffice == null)
            {
                log.error("总公司(ID=101)不存在,无法同步转运部");
                return AjaxResult.error("总公司(ID=101)不存在,请先创建总公司");
            }
            // 查询转运部是否已存在(通过部门名称和parent_id=101来查询)
            SysDept existingTransport = sysDeptMapper.checkDeptNameUnique("转运部", 101L);
            if (existingTransport != null)
            {
                // 转运部已存在
                transportDeptId = existingTransport.getDeptId();
                log.info("转运部已存在: ID={}", transportDeptId);
            }
            else
            {
                // 创建新的转运部
                SysDept newTransport = new SysDept();
                newTransport.setParentId(101L);  // 父节点为总公司
                newTransport.setDeptName("转运部");
                newTransport.setAncestors("0,101");  // 祖级列表
                newTransport.setOrderNum(1);  // 排序
                newTransport.setStatus("0");  // 正常状态
                newTransport.setCreateBy("sync");
                newTransport.setDepartmentId(150);
                sysDeptMapper.insertDept(newTransport);
                transportDeptId = newTransport.getDeptId();
                log.info("创建新转运部: ID={}", transportDeptId);
            }
            // 第二步:创建或更新转运部的子部门
            int createdDept = 0;
            int updatedDept = 0;
            for (DepartmentSyncDTO dto : transportDepts)
            {
                String deptName = dto.getDepartmentName();
                if (StringUtils.isEmpty(deptName))
                {
                    continue;
                }
                // 先根据departmentId查询是否已存在
                SysDept existingDept = sysDeptMapper.selectDeptByDepartmentIdAndParentId(
                    dto.getDepartmentId(), transportDeptId);
                if (existingDept != null)
                {
                    // 部门已存在,更新信息
                    existingDept.setDeptName(deptName);
                    existingDept.setUpdateBy("sync");
                    existingDept.setDepartmentId(dto.getDepartmentId());
                    sysDeptMapper.updateDept(existingDept);
                    updatedDept++;
                    log.info("更新转运部子部门: {}", deptName);
                }
                else
                {
                    // 检查是否存在同名部门(可能之前手动创建的)
                    SysDept sameName = sysDeptMapper.checkDeptNameUnique(deptName, transportDeptId);
                    if (sameName != null)
                    {
                        // 同名部门已存在,更新其department_id
                        sameName.setDepartmentId(dto.getDepartmentId());
                        sameName.setUpdateBy("sync");
                        sysDeptMapper.updateDept(sameName);
                        updatedDept++;
                        log.info("更新已存在的同名转运部子部门: {}, departmentId: {}",
                            deptName, dto.getDepartmentId());
                    }
                    else
                    {
                        // 创建新部门
                        SysDept newDept = new SysDept();
                        newDept.setParentId(transportDeptId);
                        newDept.setDeptName(deptName);
                        newDept.setAncestors("0,101," + transportDeptId);  // 祖级列表
                        newDept.setOrderNum(1);  // 排序
                        newDept.setStatus("0");  // 正常状态
                        newDept.setDepartmentId(dto.getDepartmentId());  // 记录SQL Server中的部门ID
                        newDept.setCreateBy("sync");
                        sysDeptMapper.insertDept(newDept);
                        createdDept++;
                        log.info("创建新转运部子部门: {}, departmentId: {}",
                            deptName, dto.getDepartmentId());
                    }
                }
            }
            String message = String.format("转运部同步完成!创建子部门: %d, 更新子部门: %d",
                createdDept, updatedDept);
            log.info(message);
            Map<String, Object> result = new HashMap<>();
            result.put("transportDeptId", transportDeptId);
            result.put("createdDept", createdDept);
            result.put("updatedDept", updatedDept);
            result.put("totalProcessed", transportDepts.size());
            return AjaxResult.success(message, result);
        }
        catch (Exception e)
        {
            log.error("同步转运部数据失败", e);
            return AjaxResult.error("同步失败: " + e.getMessage());
        }
    }
    /**
     * 同步订单编码(服务单和调度单编码)
     *
     * 根据分公司名称中的地名,自动匹配SQL Server中的编码并更新到部门对象
     *
     * @param dept 部门对象(分公司)
     * @param cityName 城市名称(如:中山、广州、湛江)
     * @param serviceOrderList 服务单编码列表(从SQL Server查询)
     * @param dispatchOrderList 调度单编码列表(从SQL Server查询)
     */
    private void syncOrderClassCodes(SysDept dept, String cityName,
                                    List<OrderClassDTO> serviceOrderList,
                                    List<OrderClassDTO> dispatchOrderList)
    {
        if (serviceOrderList == null || dispatchOrderList == null)
        {
            log.warn("编码列表为空,跳过编码同步 - 城市: {}", cityName);
            return;
        }
        try
        {
            // 匹配服务单编码
            String serviceOrderClass = matchCityNameToCode(cityName, serviceOrderList);
            if (serviceOrderClass != null)
            {
                dept.setServiceOrderClass(serviceOrderClass);
                log.info("匹配到服务单编码 - 城市: {}, 编码: {}", cityName, serviceOrderClass);
            }
            else
            {
                log.warn("未找到匹配的服务单编码 - 城市: {}", cityName);
            }
            // 匹配调度单编码
            String dispatchOrderClass = matchCityNameToCode(cityName, dispatchOrderList);
            if (dispatchOrderClass != null)
            {
                dept.setDispatchOrderClass(dispatchOrderClass);
                log.info("匹配到调度单编码 - 城市: {}, 编码: {}", cityName, dispatchOrderClass);
            }
            else
            {
                log.warn("未找到匹配的调度单编码 - 城市: {}", cityName);
            }
        }
        catch (Exception e)
        {
            log.error("同步订单编码失败 - 城市: {}", cityName, e);
        }
    }
    /**
     * 根据城市名称匹配编码
     *
     * 匹配规则:如果vtext中包含城市名称,则返回对应的vOrder2编码
     * 例如:cityName="中山", vtext="中山服务单", vOrder2="JA" -> 返回"JA"
     *
     * @param cityName 城市名称(如:中山、广州)
     * @param orderClassList 编码列表
     * @return 匹配的编码值(vOrder2),未匹配返回null
     */
    private String matchCityNameToCode(String cityName, List<OrderClassDTO> orderClassList)
    {
        if (StringUtils.isEmpty(cityName) || orderClassList == null || orderClassList.isEmpty())
        {
            return null;
        }
        // 遍历编码列表,查找包含城市名称的项
        for (OrderClassDTO dto : orderClassList)
        {
            if (dto.getVtext() != null && dto.getVtext().contains(cityName))
            {
                log.debug("城市名称匹配成功 - 城市: {}, vtext: {}, vOrder2: {}",
                    cityName, dto.getVtext(), dto.getVOrder2());
                return dto.getVOrder2();
            }
        }
        return null;
    }
}