package com.yhy.module.core.controller.admin.workbench;

import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import com.yhy.module.core.controller.admin.workbench.vo.WbUnifiedFeeConfigRespVO;
import com.yhy.module.core.controller.admin.workbench.vo.WbUnifiedFeeConfigSaveReqVO;
import com.yhy.module.core.controller.admin.workbench.vo.WbUnifiedFeeSummaryItemVO;
import com.yhy.module.core.controller.admin.quota.vo.QuotaUnifiedFeeSettingRespVO;
import com.yhy.module.core.dal.dataobject.workbench.WbUnifiedFeeConfigDO;
import com.yhy.module.core.dal.dataobject.workbench.WbUnifiedFeeSettingDO;
import com.yhy.module.core.service.workbench.WbUnifiedFeeConfigService;
import com.yhy.module.core.service.workbench.WbSnapshotReadService;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.json.JSONUtil;
import java.util.ArrayList;
import java.util.Map;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import javax.annotation.Resource;
import javax.validation.Valid;
import java.util.List;
import java.util.stream.Collectors;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;

/**
 * 工作台统一取费配置 Controller
 */
@Tag(name = "工作台 - 统一取费配置")
@RestController
@RequestMapping("/core/wb/unified-fee-config")
@Validated
public class WbUnifiedFeeConfigController {

    @Resource
    private WbUnifiedFeeConfigService wbUnifiedFeeConfigService;

    @Resource
    private WbSnapshotReadService wbSnapshotReadService;


    @GetMapping("/list")
    @Operation(summary = "获取统一取费配置列表")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    public CommonResult<List<WbUnifiedFeeConfigRespVO>> getList(@RequestParam("compileTreeId") Long compileTreeId) {
        List<WbUnifiedFeeConfigDO> list = wbUnifiedFeeConfigService.getListByCompileTreeId(compileTreeId);
        return success(convertToRespVOList(list));
    }

    @GetMapping("/list-by-rate-mode")
    @Operation(summary = "根据费率模式获取统一取费配置列表")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    @Parameter(name = "rateModeId", description = "费率模式ID", required = true)
    public CommonResult<List<WbUnifiedFeeConfigRespVO>> getListByRateMode(
            @RequestParam("compileTreeId") Long compileTreeId,
            @RequestParam("rateModeId") Long rateModeId) {
        List<WbUnifiedFeeConfigDO> list = wbUnifiedFeeConfigService.getListByCompileTreeIdAndRateModeId(compileTreeId, rateModeId);
        return success(convertToRespVOList(list));
    }

    @GetMapping("/get-by-setting")
    @Operation(summary = "根据统一取费设置ID获取配置")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    @Parameter(name = "sourceUnifiedFeeSettingId", description = "来源统一取费设置ID", required = true)
    public CommonResult<WbUnifiedFeeConfigRespVO> getBySourceUnifiedFeeSettingId(
            @RequestParam("compileTreeId") Long compileTreeId,
            @RequestParam("sourceUnifiedFeeSettingId") Long sourceUnifiedFeeSettingId) {
        WbUnifiedFeeConfigDO config = wbUnifiedFeeConfigService.getBySourceUnifiedFeeSettingId(compileTreeId, sourceUnifiedFeeSettingId);
        return success(config != null ? convertToRespVO(config) : null);
    }

    @PostMapping("/save")
    @Operation(summary = "保存统一取费配置")
    public CommonResult<Long> save(@Valid @RequestBody WbUnifiedFeeConfigSaveReqVO reqVO) {
        WbUnifiedFeeConfigDO config = convertToDO(reqVO);
        Long id = wbUnifiedFeeConfigService.saveOrUpdate(config);
        return success(id);
    }

    @PostMapping("/batch-save")
    @Operation(summary = "批量保存统一取费配置")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    @Parameter(name = "rateModeId", description = "费率模式ID", required = true)
    public CommonResult<Boolean> batchSave(
            @RequestParam("compileTreeId") Long compileTreeId,
            @RequestParam("rateModeId") Long rateModeId,
            @Valid @RequestBody List<WbUnifiedFeeConfigSaveReqVO> reqVOList) {
        List<WbUnifiedFeeConfigDO> configs = reqVOList.stream()
                .map(this::convertToDO)
                .collect(Collectors.toList());
        wbUnifiedFeeConfigService.batchSave(compileTreeId, rateModeId, configs);
        return success(true);
    }

    @DeleteMapping("/delete")
    @Operation(summary = "删除统一取费配置")
    @Parameter(name = "id", description = "配置ID", required = true)
    public CommonResult<Boolean> delete(@RequestParam("id") Long id) {
        wbUnifiedFeeConfigService.delete(id);
        return success(true);
    }

    @PostMapping("/apply")
    @Operation(summary = "应用统一取费 - 将统一取费目录按范围添加到对应清单")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    public CommonResult<Boolean> apply(@RequestParam("compileTreeId") Long compileTreeId) {
        wbUnifiedFeeConfigService.applyUnifiedFee(compileTreeId);
        return success(true);
    }

    @GetMapping("/setting-parent-list")
    @Operation(summary = "获取统一取费设置父列表（从快照表读取）")
    @Parameter(name = "compileTreeId", description = "单位工程节点ID", required = true)
    @Parameter(name = "rateModeId", description = "费率模式ID", required = true)
    public CommonResult<List<QuotaUnifiedFeeSettingRespVO>> getSettingParentList(
            @RequestParam("compileTreeId") Long compileTreeId,
            @RequestParam("rateModeId") Long rateModeId) {
        // 从快照表读取统一取费设置
        List<WbUnifiedFeeSettingDO> snapshotItems = wbSnapshotReadService.getUnifiedFeeSettings(compileTreeId, rateModeId);
        
        // 按parentId分组
        Map<Long, List<WbUnifiedFeeSettingDO>> childrenMap = snapshotItems.stream()
            .filter(item -> item.getParentId() != null)
            .collect(Collectors.groupingBy(WbUnifiedFeeSettingDO::getParentId));
        
        // 构建树形结构：directory → fee(parent) → sub_fee(child)
        List<QuotaUnifiedFeeSettingRespVO> result = snapshotItems.stream()
            .filter(item -> item.getParentId() == null) // 一级节点（目录或费用）
            .map(rootItem -> buildSnapshotTreeNode(rootItem, childrenMap))
            .collect(Collectors.toList());
        
        return success(result);
    }

    @GetMapping("/summary-source")
    @Operation(summary = "获取统一取费汇总来源 - 返回范围内的定额列表")
    @Parameter(name = "divisionId", description = "统一取费节点ID", required = true)
    public CommonResult<List<WbUnifiedFeeSummaryItemVO>> getSummarySource(
            @RequestParam("divisionId") Long divisionId) {
        List<WbUnifiedFeeSummaryItemVO> list = wbUnifiedFeeConfigService.getSummarySourceByDivisionId(divisionId);
        return success(list);
    }

    private WbUnifiedFeeConfigRespVO convertToRespVO(WbUnifiedFeeConfigDO config) {
        WbUnifiedFeeConfigRespVO respVO = new WbUnifiedFeeConfigRespVO();
        respVO.setId(config.getId());
        respVO.setCompileTreeId(config.getCompileTreeId());
        respVO.setDivisionId(config.getDivisionId());
        respVO.setSourceUnifiedFeeSettingId(config.getSourceUnifiedFeeSettingId());
        respVO.setRateModeId(config.getRateModeId());
        respVO.setConfigData(config.getConfigData());
        respVO.setAttributes(config.getAttributes());
        respVO.setSortOrder(config.getSortOrder());
        return respVO;
    }

    private List<WbUnifiedFeeConfigRespVO> convertToRespVOList(List<WbUnifiedFeeConfigDO> list) {
        return list.stream().map(this::convertToRespVO).collect(Collectors.toList());
    }

    private WbUnifiedFeeConfigDO convertToDO(WbUnifiedFeeConfigSaveReqVO reqVO) {
        WbUnifiedFeeConfigDO config = new WbUnifiedFeeConfigDO();
        config.setId(reqVO.getId());
        config.setCompileTreeId(reqVO.getCompileTreeId());
        config.setDivisionId(reqVO.getDivisionId());
        config.setSourceUnifiedFeeSettingId(reqVO.getSourceUnifiedFeeSettingId());
        config.setRateModeId(reqVO.getRateModeId());
        config.setConfigData(reqVO.getConfigData());
        config.setAttributes(reqVO.getAttributes());
        config.setSortOrder(reqVO.getSortOrder());
        return config;
    }

    /**
     * 递归构建快照树节点，并合并子节点的feeChapter
     */
    private QuotaUnifiedFeeSettingRespVO buildSnapshotTreeNode(WbUnifiedFeeSettingDO item, Map<Long, List<WbUnifiedFeeSettingDO>> childrenMap) {
        QuotaUnifiedFeeSettingRespVO vo = BeanUtil.copyProperties(item, QuotaUnifiedFeeSettingRespVO.class);
        // 使用快照表的sourceId作为id，保持与后台标准库的兼容性
        vo.setId(item.getSourceId());
        
        List<WbUnifiedFeeSettingDO> children = childrenMap.get(item.getId());
        if (children != null && !children.isEmpty()) {
            // 递归构建子节点
            List<QuotaUnifiedFeeSettingRespVO> childVOs = children.stream()
                .map(child -> buildSnapshotTreeNode(child, childrenMap))
                .collect(Collectors.toList());
            vo.setChildren(childVOs);
            
            // 合并所有子孙节点的feeChapter到当前节点
            List<String> allChapters = new ArrayList<>();
            collectSnapshotFeeChapters(childVOs, allChapters);
            if (!allChapters.isEmpty()) {
                vo.setFeeChapter(JSONUtil.toJsonStr(allChapters));
            }
        }
        return vo;
    }
    
    /**
     * 递归收集所有子孙节点的feeChapter
     */
    private void collectSnapshotFeeChapters(List<QuotaUnifiedFeeSettingRespVO> nodes, List<String> result) {
        for (QuotaUnifiedFeeSettingRespVO node : nodes) {
            // 收集当前节点的feeChapter
            String fc = node.getFeeChapter();
            if (fc != null && !fc.isEmpty() && !"[]".equals(fc)) {
                try {
                    List<String> ids = JSONUtil.toList(fc, String.class);
                    result.addAll(ids);
                } catch (Exception e) {
                    // 解析失败时忽略
                }
            }
            // 递归收集子节点
            if (node.getChildren() != null && !node.getChildren().isEmpty()) {
                collectSnapshotFeeChapters(node.getChildren(), result);
            }
        }
    }
}
