package com.yhy.module.core.service.workbench;

import cn.iocoder.yudao.framework.common.pojo.PageResult;
import com.yhy.module.core.controller.admin.workbench.vo.HistoryBoqListReqVO;
import com.yhy.module.core.controller.admin.workbench.vo.WbBoqDivisionRespVO;
import com.yhy.module.core.controller.admin.workbench.vo.WbBoqDivisionSaveReqVO;
import com.yhy.module.core.controller.admin.workbench.vo.WbBoqDivisionSwapSortReqVO;
import com.yhy.module.core.controller.admin.workbench.vo.calcbaserate.UpdateBoqDivisionBaseRateReqVO;
import java.util.List;
import javax.validation.Valid;

/**
 * 工作台分部分项树 Service 接口
 *
 * @author yhy
 */
public interface WbBoqDivisionService {

    /**
     * 创建节点（分部、清单或定额）
     *
     * @param createReqVO 创建信息
     * @return 节点ID
     */
    Long createNode(@Valid WbBoqDivisionSaveReqVO createReqVO);

    /**
     * 更新节点
     *
     * @param updateReqVO 更新信息
     */
    void updateNode(@Valid WbBoqDivisionSaveReqVO updateReqVO);

    /**
     * 删除节点
     *
     * @param id 节点ID
     */
    void deleteNode(Long id);

    /**
     * 获取节点详情
     *
     * @param id 节点ID
     * @return 节点详情
     */
    WbBoqDivisionRespVO getNode(Long id);

    /**
     * 获取单位工程的分部分项树
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @return 树形结构
     */
    List<WbBoqDivisionRespVO> getTree(Long compileTreeId);

    /**
     * 获取单位工程的分部分项树（支持过滤工程量为0的清单）
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param excludeZeroQtyBoq 是否过滤工程量为0或空的清单节点
     * @return 树形结构
     */
    List<WbBoqDivisionRespVO> getTree(Long compileTreeId, Boolean excludeZeroQtyBoq);

    /**
     * 交换排序
     *
     * @param swapReqVO 交换信息
     */
    void swapSort(@Valid WbBoqDivisionSwapSortReqVO swapReqVO);

    /**
     * 根据单位工程节点ID删除所有分部分项
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     */
    void deleteByCompileTreeId(Long compileTreeId);

    /**
     * 获取单位工程的分部分项树（含定额单价计算）
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @return 树形结构（定额节点包含计算后的单价和合价）
     */
    List<WbBoqDivisionRespVO> getTreeWithPrice(Long compileTreeId);

    /**
     * 获取单位工程的分部分项树（含定额单价计算，调试模式）
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param debug 是否返回调试信息
     * @return 树形结构（定额节点包含计算后的单价和合价）
     */
    List<WbBoqDivisionRespVO> getTreeWithPrice(Long compileTreeId, boolean debug);

    /**
     * 创建分部分项根目录节点（系统自动创建，用于单位工程创建时）
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param unitName 单位工程名称
     * @return 根目录节点ID
     */
    Long createRootNode(Long compileTreeId, String unitName);

    /**
     * 获取租户所有清单节点（历史套用）
     *
     * @return 清单节点列表
     */
    List<WbBoqDivisionRespVO> getAllBoqNodes();

    /**
     * 复制清单到目标位置（含定额和工料机）
     *
     * @param sourceBoqId 源清单节点ID
     * @param targetCompileTreeId 目标单位工程节点ID
     * @param targetParentId 目标父节点ID（分部或清单的父节点）
     * @return 新创建的清单节点ID
     */
    Long copyBoqWithChildren(Long sourceBoqId, Long targetCompileTreeId, Long targetParentId);

    /**
     * 获取历史清单/分部列表（支持查询条件，分页）
     *
     * @param reqVO 查询参数（含分页）
     * @return 清单/分部节点分页结果
     */
    PageResult<WbBoqDivisionRespVO> getHistoryListPage(HistoryBoqListReqVO reqVO);

    /**
     * 复制分部到目标位置（含子清单、定额和工料机）
     *
     * @param sourceDivisionId 源分部节点ID
     * @param targetCompileTreeId 目标单位工程节点ID
     * @param targetParentId 目标父节点ID
     * @return 新创建的分部节点ID
     */
    Long copyDivisionWithChildren(Long sourceDivisionId, Long targetCompileTreeId, Long targetParentId);

    /**
     * 从清单指引复制清单子目到分部分项（含定额和工料机）
     *
     * @param compileTreeId 目标单位工程节点ID
     * @param parentId 目标父节点ID（必须是分部节点）
     * @param boqSubItemId 清单子目ID（标准库）
     * @param sourceBoqItemTreeId 清单项树节点ID（标准库）
     * @return 新创建的清单节点ID
     */
    Long copyFromGuide(Long compileTreeId, Long parentId, Long boqSubItemId, Long sourceBoqItemTreeId);

    /**
     * 更新清单的基数费率
     *
     * @param reqVO 更新信息
     */
    void updateBoqDivisionBaseRate(@Valid UpdateBoqDivisionBaseRateReqVO reqVO);

    /**
     * 导入模板到工作台（从后台单位工程界面配置复制分部分项模板和标签页引用）
     *
     * @param compileTreeId 单位工程节点ID
     * @param catalogItemId fields_majors 节点ID（用于查询模板）
     */
    void importTemplate(Long compileTreeId, Long catalogItemId);

    /**
     * 按标签页获取分部分项树
     * - tabType=division 或 null：返回全量树（数据总线完整视图）
     * - tabType=measure/other/unit_summary：只返回对应 tabType 的节点及其子节点
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param tabType 标签页类型（division/measure/other/unit_summary）
     * @return 树形结构
     */
    List<WbBoqDivisionRespVO> getTreeByTab(Long compileTreeId, String tabType);

    /**
     * 按标签页获取分部分项树（支持过滤工程量为0的清单）
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param tabType 标签页类型（division/measure/other/unit_summary）
     * @param excludeZeroQtyBoq 是否过滤工程量为0或空的清单节点
     * @return 树形结构
     */
    List<WbBoqDivisionRespVO> getTreeByTab(Long compileTreeId, String tabType, Boolean excludeZeroQtyBoq);

    /**
     * 获取统一取费范围选择树
     * 专供统一取费弹窗使用，按标签页过滤后：
     * 1. 过滤掉 unified_fee 类型节点
     * 2. 如果传了 feeChapter，根据取费章节过滤定额，并裁剪空清单
     *
     * @param compileTreeId 编制模式树的单位工程节点ID
     * @param tabType 标签页类型（division/measure）
     * @param feeChapter 取费章节ID列表（可选，为空则不过滤定额）
     * @return 树形结构
     */
    List<WbBoqDivisionRespVO> getTreeForUnifiedFee(Long compileTreeId, String tabType, List<Long> feeChapter);
}
