package com.njcn.relational.service.impl;

import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.njcn.relational.pojo.dto.DcloudSyncQuery;
import com.njcn.relational.service.*;
import dcloud.common.InnerServiceBus.ServiceBus;
import dcloud.model.common.ConModel;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

/**
 * @Author: cdf
 * @CreateTime: 2026-06-17
 * @Description: 云平台模型服务实现类
 */
@Service
@RequiredArgsConstructor
@Slf4j
public class DcloudBusServiceImpl implements DcloudBusService {

    private static final String MODEL_STR = "dcloud.model.common.ConModel";
    private static final int DEFAULT_PAGE_SIZE = 1000;
    private static final int MAX_RETRY = 3;

    private final SgConPlantCService sgConPlantCService;

    private final SGConPlantBService sgConPlantBService;

    private final SGConSubstationBService sgConSubstationBService;

    private final SGConSubstationCService sgConSubstationCService;

    private final SgConPlantBNewenergyService sgConPlantBNewenergyService;

    private final SgDevAclineBService sgDevAclineBService;


    /**
     * 数据入库入口
     */
    @Override
    public boolean syncDataToDb(DcloudSyncQuery query) {
        log.info("开始从云平台同步厂站数据到本地数据库");

        ServiceBus serviceBus = initServiceBus();
        if (serviceBus == null) {
            log.error("ServiceBus初始化失败，终止同步");
            return false;
        }

        try {
            handleConModelSync(serviceBus, query);
            log.info("厂站数据同步完成");
            return true;
        } catch (Exception e) {
            log.error("厂站数据同步失败", e);
            return false;
        }
    }


    /**
     * 统一同步入口
     */
    public void syncData(DcloudSyncQuery query) {
        query.emptyCover();
        String tableName = query.getTableName();
        log.info("【{}】开始同步数据，查询参数：{}", MODEL_STR, query);

        ServiceBus serviceBus = initServiceBus();
        if (serviceBus == null) {
            log.error("ServiceBus初始化失败，终止同步，tableName={}", tableName);
            return;
        }

        handleConModelSync(serviceBus, query);
    }

    /**
     * 初始化服务总线
     */
    private ServiceBus initServiceBus() {
        ServiceBus bus = new ServiceBus();
        try {
            bus.init();
            log.info("ServiceBus初始化成功");
            return bus;
        } catch (Exception e) {
            log.error("ServiceBus初始化异常", e);
            return null;
        }
    }

    /**
     * 获取数据总数
     */
    private Integer getDataSize(ConModel model, String tableName, String filter) {
        try {
            JSONObject result = model.getDataSize(tableName, filter);
            log.info("[{}] 获取数据总数，filter: {}", tableName, filter);

            if (result == null) {
                log.error("[{}] 获取数据总数返回空", tableName);
                return 0;
            }

            String code = StrUtil.nullToEmpty(result.getString("code"));
            if (!"200".equals(code)) {
                log.error("[{}] 获取数据总数失败，响应码：{}", tableName, code);
                return 0;
            }

            Integer dataSize = result.getInteger("dataSize");
            log.info("[{}] 数据总数: {}", tableName, dataSize);
            return dataSize != null ? dataSize : 0;
        } catch (Exception e) {
            log.error("[{}] 获取数据总数异常", tableName, e);
            return 0;
        }
    }

    /**
     * 分页查询数据
     */
    private JSONArray getDataList(ConModel model, DcloudSyncQuery query, int pageIndex, int pageSize) {
        try {
            JSONObject result = model.getDataList(
                    query.getTableName(),
                    pageSize,
                    pageIndex,
                    query.getFilter(),
                    query.getOrderStr(),
                    query.getPropertyList()
            );

            if (result == null) {
                log.error("[{}] 分页查询返回空，pageIndex: {}", query.getTableName(), pageIndex);
                return new JSONArray();
            }

            String code = StrUtil.nullToEmpty(result.getString("code"));
            if (!"200".equals(code)) {
                log.error("[{}] 分页查询失败，响应码：{}，pageIndex: {}", query.getTableName(), code, pageIndex);
                return new JSONArray();
            }

            JSONArray dataArr = result.getJSONArray("data");
            return dataArr != null ? dataArr : new JSONArray();
        } catch (Exception e) {
            log.error("[{}] 分页查询异常，pageIndex: {}", query.getTableName(), pageIndex, e);
            return new JSONArray();
        }
    }

    /**
     * ConModel模型同步逻辑（先查总数，再分批查询入库）
     */
    private void handleConModelSync(ServiceBus bus, DcloudSyncQuery query) {
        String tableName = query.getTableName();
        int successCount = 0;
        int failCount = 0;

        try {
            ConModel model = (ConModel) bus.locateService(MODEL_STR);

            // 1. 先查询总数
            Integer totalCount = getDataSize(model, tableName, query.getFilter());
            if (totalCount == null || totalCount == 0) {
                log.info("[{}] 无数据需要同步", tableName);
                return;
            }
            log.info("[{}] 总共需要同步 {} 条数据", tableName, totalCount);

            // 2. 计算分页参数
            int pageSize = query.getPageSize() != null ? query.getPageSize() : DEFAULT_PAGE_SIZE;
            int totalPages = (totalCount + pageSize - 1) / pageSize;
            log.info("[{}] 分页参数: 每页{}条, 共{}页", tableName, pageSize, totalPages);

            // 3. 分批查询并入库
            for (int pageIndex = 1; pageIndex <= totalPages; pageIndex++) {
                log.info("[{}] 开始查询第 {}/{} 页", tableName, pageIndex, totalPages);

                // 带重试的分页查询
                JSONArray pageData = null;
                for (int retry = 0; retry < MAX_RETRY; retry++) {
                    pageData = getDataList(model, query, pageIndex, pageSize);
                    if (pageData != null && !pageData.isEmpty()) {
                        break;
                    }
                    if (retry < MAX_RETRY - 1) {
                        log.warn("[{}] 第{}页查询失败(第{}次重试)，等待后重试", tableName, pageIndex, retry + 1);
                        try {
                            Thread.sleep(1000 * (retry + 1));
                        } catch (InterruptedException e) {
                            Thread.currentThread().interrupt();
                        }
                    }
                }

                if (pageData == null || pageData.isEmpty()) {
                    log.warn("[{}] 第{}页无数据，跳过", tableName, pageIndex);
                    failCount++;
                    continue;
                }

                log.info("[{}] 第{}页查询到 {} 条数据，开始入库", tableName, pageIndex, pageData.size());

                // 分批入库（每页数据直接入库）
                boolean batchResult = false;
                if("SG_CON_PLANT_C".equals(tableName)) {
                    log.info("【全量同步入口】执行同步厂站基础数据---------");
                    batchResult = sgConPlantCService.batchSyncFromDcloud(pageData);
                }else if("SG_CON_PLANT_B".equals(tableName)){
                    log.info("【全量同步入口】执行同步厂站绑定数据1111111111");
                    batchResult = sgConPlantBService.batchSyncFromDcloud(pageData);
                }else if("SG_CON_SUBSTATION_B".equals(tableName)){
                    log.info("【全量同步入口】执行变电站站基础数据---------");
                    batchResult = sgConSubstationBService.batchSyncFromDcloud(pageData);
                }else if("SG_CON_SUBSTATION_C".equals(tableName)){
                    log.info("【全量同步入口】执行变电站站绑定数据---------");
                    batchResult = sgConSubstationCService.batchSyncFromDcloud(pageData);
                }else if("SG_CON_PLANT_B_NEWENERGY".equals(tableName)){
                    log.info("【全量同步入口】执行新能源场站基本信息---------");
                    batchResult = sgConPlantBNewenergyService.batchSyncFromDcloud(pageData);
                }else if("SG_DEV_ACLINE_B".equals(tableName)){
                    log.info("【全量同步入口】执行线路表同步---------");
                    batchResult = sgDevAclineBService.batchSyncFromDcloud(pageData);
                }
                if (batchResult) {
                    successCount += pageData.size();
                    log.info("[{}] 第{}页入库成功，当前累计成功 {} 条", tableName, pageIndex, successCount);
                } else {
                    failCount += pageData.size();
                    log.error("[{}] 第{}页入库失败", tableName, pageIndex);
                }
            }

            log.info("[{}] 同步完成: 成功={}, 失败={}, 总计={}", tableName, successCount, failCount, totalCount);

        } catch (Exception e) {
            log.error("[{}] ConModel同步数据异常", tableName, e);
        }
    }


    // ===================== 便捷方法 =====================

    /**
     * 快速同步厂站表数据
     */
    public void syncPlantConData(Integer pageIndex, Integer pageSize, String filter, String orderStr) {
        DcloudSyncQuery query = DcloudSyncQuery.buildPlantDefault(filter, orderStr, pageIndex, pageSize);
        syncData(query);
    }

    /**
     * 快速同步厂站表数据（使用默认分页）
     */
    public void syncPlantConData() {
        syncPlantConData(1, DEFAULT_PAGE_SIZE, null, null);
    }

    /**
     * 根据更新时间增量同步厂站数据
     */
    public void syncPlantConDataByUpdateTime(String updateTime) {
        String filter = "UPDATE_TIME >= '" + updateTime + "'";
        DcloudSyncQuery query = DcloudSyncQuery.buildPlantDefault(filter, null, 1, DEFAULT_PAGE_SIZE);
        syncData(query);
    }

    /**
     * 根据ID同步指定厂站数据
     */
    public void syncPlantConDataById(String dcloudId) {
        String filter = "ID = '" + dcloudId + "'";
        DcloudSyncQuery query = DcloudSyncQuery.buildPlantDefault(filter, null, 1, DEFAULT_PAGE_SIZE);
        syncData(query);
    }
}