package com.chinaweal.aiccs.schedule;

import cn.hutool.core.codec.Base64;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.extra.ftp.Ftp;
import cn.hutool.extra.ftp.FtpConfig;
import cn.hutool.extra.ftp.FtpMode;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.chinaweal.aiccs.aiccs.abnormal.entity.CaseZfReport;
import com.chinaweal.aiccs.aiccs.abnormal.entity.TSWrit;
import com.chinaweal.aiccs.aiccs.abnormal.mapper.CaseZfReportMapper;
import com.chinaweal.aiccs.aiccs.abnormal.mapper.TSWritMapper;
import com.chinaweal.aiccs.aiccs.auditing.entity.TSOpinion;
import com.chinaweal.aiccs.aiccs.auditing.service.TSOpinionService;
import com.chinaweal.aiccs.aiccs.revoke.entity.*;
import com.chinaweal.aiccs.aiccs.revoke.mapper.*;
import com.chinaweal.aiccs.aiccs.abnormal.mapper.EBaseinfoMapper;
import com.chinaweal.aiccs.aiccs.abnormal.entity.EBaseinfo;
import com.chinaweal.aiccs.aiccs.revoke.service.IllegalactService;
import com.chinaweal.aiccs.common.constant.BaseDataConstant;
import com.chinaweal.aiccs.crgs.entity.EPriPersonCrgs;
import com.chinaweal.aiccs.crgs.service.EPriPersonCrgsService;
import com.chinaweal.aiccs.outside.api.CaseUploadApi;
import com.chinaweal.solr.util.StringUtils;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.util.*;
import java.time.format.DateTimeFormatter;
import com.alibaba.fastjson.JSON;
/**
 * 附件上传定时任务
 * 功能：从FTP下载附件，重命名后通过API上传到第三方系统
 *
 * @author Claude
 */
@Component
@ConditionalOnProperty(prefix = "scheduling", name = "enable", havingValue = "true")
@Slf4j
public class AttachmentUploadSchedule {

    @Autowired
    private CaseZfReportMapper caseZfReportMapper;

    @Autowired
    private TSWritMapper tswritMapper;

    @Autowired
    private TsbizrevlistMapper tsbizrevlistMapper;

    @Autowired
    private BizRevEntMapper bizRevEntMapper;

    @Autowired
    private CaseMapper caseMapper;

    @Autowired
    private TsrevtasklistMapper tsrevtasklistMapper;

    @Autowired
    private RevokelistMapper revokelistMapper;

    @Autowired
    private EBaseinfoMapper eBaseinfoMapper;

    @Autowired
    private CaseUploadApi caseUploadApi;

    @Autowired
    private IllegalactMapper illegalactMapper;

    @Autowired
    private TshearingreportMapper tshearingreportMapper;

    @Autowired
    private EPriPersonCrgsService ePriPersonCrgsService;

    @Autowired
    private TSOpinionService opinionService;


    // 现有FTP配置（从配置文件读取）
    @Value("${storage.ftp.ip}")
    private String localFtpIp;

    @Value("${storage.ftp.port}")
    private int localFtpPort;

    @Value("${storage.ftp.username}")
    private String localFtpUsername;

    @Value("${storage.ftp.password}")
    private String localFtpPassword;

    // 第三方FTP配置
    private final String THIRD_FTP_IP = "19.16.192.132";
    private final int THIRD_FTP_PORT = 21;
    private final String THIRD_FTP_USERNAME = "scjg";
    private final String THIRD_FTP_PASSWORD = "1qaz@WSX#241017";
    private final String THIRD_FTP_DIRECTORY = "/GZ/GZSCJG";

    // 测试环境目录（使用本地FTP模拟第三方FTP）
    private final String TEST_DIRECTORY = "/GZ/GZSCJG";

    // API上传配置
    private final String API_URL = "/api/v1/cases";
    private final String API_KEY = "1V71cx6AolVdIGrLSEWdgV";
    private final String DEFAULT_UPDATE_TYPE = "create";
    private final String DEFAULT_CASE_TYPE = "2"; // 普通案件

    /**
     * 定时任务方法 - 每天凌晨2点执行
     */
    @Scheduled(cron = "${scheduling.cron.attachmentUpload}")
    public void executeAttachmentUpload() {
        log.info("开始执行附件上传定时任务...");

        try {
            // 第一步：查询未上传成功的数据
            List<CaseZfReport> reportList = queryPendingReports();
            log.info("查询到{}条待处理的记录", reportList.size());

            for (CaseZfReport report : reportList) {
                try {
                    processSingleReport(report);
                } catch (Exception e) {
                    log.error("处理记录{}时发生错误", report.getId(), e);
                    // 更新状态为失败
                    updateReportStatus(report.getId(), "1");
                }
            }

            log.info("附件上传定时任务执行完成");
        } catch (Exception e) {
            log.error("附件上传定时任务执行失败", e);
        }
    }

    /**
     * 查询待处理的报告记录
     */
    private List<CaseZfReport> queryPendingReports() {
        QueryWrapper<CaseZfReport> queryWrapper = new QueryWrapper<>();
        // 组合条件：(ISFY != '0' 或者 ISFY 为 NULL) 并且 XTPATH 不为空且不为空字符串
        queryWrapper.and(w -> w.ne("ISFY", "0").or().isNull("ISFY")) // 关键：包含非0和NULL
                .isNotNull("XTPATH")
                .ne("XTPATH", "");

        return caseZfReportMapper.selectList(queryWrapper);
    }

    /**
     * 处理单个报告记录
     */
    private void processSingleReport(CaseZfReport report) {
        String xtpath = report.getXtpath();
        if (StrUtil.isBlank(xtpath)) {
            log.warn("记录{}的XTPATH为空，跳过处理", report.getId());
            return;
        }

        // 第一步：从现有FTP下载文件
        File tempFile = downloadFromLocalFtp(xtpath);
        if (tempFile == null || !tempFile.exists()) {
            log.warn("无法下载文件：{}，跳过记录{}", xtpath, report.getId());
            updateReportStatus(report.getId(), "1");
            return;
        }

        try {
            // 第二步：查询文书编号并重命名文件
            String newFileName = generateNewFileName(report, xtpath);
            if (StrUtil.isBlank(newFileName)) {
                log.warn("无法获取新的文件名，跳过记录{}", report.getId());
                updateReportStatus(report.getId(), "1");
                return;
            }

            File renamedFile = new File(tempFile.getParent(), newFileName);
            tempFile.renameTo(renamedFile);

            // 第三步：通过API上传文件并获取上传结果
            String zfpath = uploadFileViaApi(renamedFile, newFileName, report);

            // 更新状态
            if (zfpath != null) {
                // 上传成功，更新状态和上传路径
                updateReportStatusAndPath(report.getId(), "0", zfpath);
            } else {
                // 上传失败
                updateReportStatus(report.getId(), "1");
            }

            // 清理临时文件
            FileUtil.del(renamedFile);

        } catch (Exception e) {
            log.error("处理报告{}时发生错误", report.getId(), e);
            updateReportStatus(report.getId(), "1");
            // 清理临时文件
            FileUtil.del(tempFile);
        }
    }

    /**
     * 从现有FTP下载文件
     */
    private File downloadFromLocalFtp(String remotePath) {
        FtpConfig ftpConfig = new FtpConfig(localFtpIp, localFtpPort, localFtpUsername, localFtpPassword, StandardCharsets.UTF_8);
        ftpConfig.setConnectionTimeout(30000);
        ftpConfig.setSoTimeout(30000);

        try (Ftp ftp = new Ftp(ftpConfig, FtpMode.Passive)) {
            // 创建临时文件
            File tempFile = java.io.File.createTempFile("temp", ".tmp", new File(System.getProperty("java.io.tmpdir")));

            String fileName = FileUtil.getName(remotePath);
            String dirPath = StrUtil.removeSuffix(remotePath, fileName);

            // 下载文件
            ftp.download(dirPath, fileName, tempFile);
            boolean success = tempFile.exists() && tempFile.length() > 0;
            if (success) {
                log.debug("成功下载文件：{}", remotePath);
                return tempFile;
            } else {
                log.warn("下载文件失败：{}", remotePath);
                FileUtil.del(tempFile);
                return null;
            }
        } catch (Exception e) {
            log.error("从FTP下载文件{}时发生错误", remotePath, e);
            return null;
        }
    }

    /**
     * 生成新的文件名
     */
    private String generateNewFileName(CaseZfReport report, String originalPath) {
        try {
            // 查询TSwrit表获取WRITSNO
            QueryWrapper<TSWrit> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("BIZSEQ", report.getBizseq())
                    .eq("PRIPID", report.getPripid())
                    .eq("WRITSTYPE", "33");

            TSWrit tswrit = tswritMapper.selectOne(queryWrapper);
            if (tswrit == null || StrUtil.isBlank(tswrit.getWritsno())) {
                log.warn("未找到对应的文书号信息：BIZSEQ={}, PRIPID={}", report.getBizseq(), report.getPripid());
                return null;
            }

            String originalFileName = FileUtil.getName(originalPath);
            String extension = FileUtil.extName(originalFileName);

            // 使用文书号作为新文件名
            String newFileName = report.getCaseno();
            if (StrUtil.isNotBlank(extension)) {
                newFileName += "." + extension.toUpperCase();
            }

            log.debug("生成新文件名：{} -> {}", originalFileName, newFileName);
            return newFileName;

        } catch (Exception e) {
            log.error("生成新文件名时发生错误", e);
            return null;
        }
    }


    /**
     * 通过API上传文件并返回上传结果
     */
    private String uploadFileViaApi(File file, String fileName, CaseZfReport report) {
        try {
            // 读取文件内容并转换为Base64
            byte[] fileBytes = FileUtil.readBytes(file);
            String base64Content = Base64.encode(fileBytes);

            // 构造请求体数据
            Map<String, Object> requestBody = new HashMap<>();
            requestBody.put("updateType", DEFAULT_UPDATE_TYPE);
            requestBody.put("caseType", DEFAULT_CASE_TYPE);
//            requestBody.put("qt", "");
//            requestBody.put("jbdw", "");

            // 构造完整的caseInfo对象（根据您提供的完整示例数据结构）
            Map<String, Object> caseInfo = buildCompleteCaseInfo(fileName, base64Content, report);

            requestBody.put("caseInfo", caseInfo);

            // 发送POST请求到API
            log.info("准备通过API上传文件: {}, 大小: {} 字节", fileName, fileBytes.length);
            log.debug("请求体数据: {}", JSON.toJSONString(requestBody));

            // 使用Forest框架发送POST请求
            com.dtflys.forest.http.ForestResponse<String> response = caseUploadApi.uploadCase(API_KEY, requestBody);

            if (response.isSuccess()) {
                String responseBody = response.getResult();
                log.info("文件{}通过API上传完成，响应: {}", fileName, responseBody);

                // 解析响应，根据API返回结构处理三种情况
                try {
                    JSONObject jsonResponse = JSON.parseObject(responseBody);
                    int code = jsonResponse.getIntValue("code");
                    String message = jsonResponse.getString("message");

                    // 情况1: code 200 - 成功
                    if (code == 200) {
                        JSONObject data = jsonResponse.getJSONObject("data");
                        if (data != null) {
                            String caseId = data.getString("caseId");
                            String status = data.getString("status");
                            String dataMessage = data.getString("message");

                            log.info("案件上传成功，案件ID: {}, 状态: {}, 消息: {}", caseId, status, dataMessage);
                            return caseId; // 返回案件ID作为成功标识
                        }
                    }
                    // 情况2: code 400 - 请求参数错误
                    else if (code == 400) {
                        JSONObject data = jsonResponse.getJSONObject("data");
                        if (data != null) {
                            String caseId = data.getString("caseId");
                            String status = data.getString("status");
                            String dataMessage = data.getString("message");

                            log.error("案件上传失败，请求参数错误，案件ID: {}, 状态: {}, 错误信息: {}", caseId, status, dataMessage);
                        } else {
                            log.error("案件上传失败，请求参数错误，错误信息: {}", message);
                        }
                        return null; // 返回null表示上传失败
                    }
                    // 情况3: code 401 - 认证失败
                    else if (code == 401) {
                        log.error("案件上传失败，认证失败，错误信息: {}", message);
                        return null; // 返回null表示上传失败
                    }
                    // 其他情况
                    else {
                        log.error("案件上传失败，未知响应码: {}, 错误信息: {}", code, message);
                        return null; // 返回null表示上传失败
                    }
                } catch (Exception parseEx) {
                    log.error("解析API响应时发生错误，响应内容: {}", responseBody, parseEx);
                    return null; // 返回null表示上传失败
                }
            } else {
                log.error("文件{}通过API上传失败，状态码: {}, 错误信息: {}", fileName, response.getStatusCode(), response.readAsString());
                return null;
            }

        } catch (Exception e) {
            log.error("通过API上传文件{}时发生错误", fileName, e);
            return null; // 返回null表示上传失败
        }

        // 默认返回null（理论上不会执行到这里）
        return null;
    }

    /**
     * 构造完整的caseInfo对象（根据您提供的完整示例数据结构）
     */
    private Map<String, Object> buildCompleteCaseInfo(String fileName, String base64Content, CaseZfReport report) {
        Map<String, Object> caseInfo = new HashMap<>();



        // 查询相关实体信息
        String bizseq = report.getBizseq();
        String pripid = report.getPripid();

        // 1. 查询tsbizrevlist信息
        QueryWrapper<Tsbizrevlist> tsbizrevlistQueryWrapper = new QueryWrapper<>();
        tsbizrevlistQueryWrapper.eq("BIZSEQ", bizseq).eq("PRIPID", pripid);
        Tsbizrevlist tsbizrevlist = tsbizrevlistMapper.selectOne(tsbizrevlistQueryWrapper);

        // 2. 查询BizRevEnt信息
        QueryWrapper<BizRevEnt> bizRevEntQueryWrapper = new QueryWrapper<>();
        bizRevEntQueryWrapper.eq("BIZSEQ", bizseq).eq("PRIPID", pripid);
        BizRevEnt bizRevEnt = bizRevEntMapper.selectOne(bizRevEntQueryWrapper);

        // 3. 查询tswrit信息（已经在方法中使用了，可以直接复用）
        QueryWrapper<TSWrit> tswritQueryWrapper = new QueryWrapper<>();
        tswritQueryWrapper.eq("BIZSEQ", bizseq).eq("PRIPID", pripid).eq("WRITSTYPE", "33");
        TSWrit tswrit = tswritMapper.selectOne(tswritQueryWrapper);

        // 4. 查询tscase信息
        QueryWrapper<TsCase> tsCaseQueryWrapper = new QueryWrapper<>();
        tsCaseQueryWrapper.eq("bizseq", bizseq);
        TsCase tsCase = caseMapper.selectOne(tsCaseQueryWrapper);


        // 5. 查询Tsrevtasklist信息
        QueryWrapper<Tsrevtasklist> tsrevtasklistQueryWrapper = new QueryWrapper<>();
        tsrevtasklistQueryWrapper.eq("BIZSEQID", bizseq);
        List<Tsrevtasklist> tsrevtasklists = tsrevtasklistMapper.selectList(tsrevtasklistQueryWrapper);
        Tsrevtasklist tsrevtasklist = tsrevtasklists.get(0);

        // 6. 查询Revokelist信息
        Revokelist revokelist = null;
        if (tsCase != null && tsCase.getCaseNo() != null) {
            QueryWrapper<Revokelist> revokelistQueryWrapper = new QueryWrapper<>();
            revokelistQueryWrapper.eq("CASENO", tsCase.getCaseNo()).eq("PRIPID", pripid);
            revokelist = revokelistMapper.selectOne(revokelistQueryWrapper);
        }

        // 7. 查询EBaseinfo信息
        EBaseinfo eBaseinfo = eBaseinfoMapper.selectById(pripid);

        // 8. 查询Illegalact信息
        QueryWrapper<Illegalact> illegalactQueryWrapper = new QueryWrapper<>();
        illegalactQueryWrapper.eq("caseId", tsCase.getCaseId());
        Illegalact illegalact = illegalactMapper.selectOne(illegalactQueryWrapper);


        // 9. 查询tsHearingReport信息
        QueryWrapper<TsHearingReport> tsHearingReportQueryWrapper = new QueryWrapper<>();
        tsHearingReportQueryWrapper.eq("BIZSEQ", bizseq).eq("PRIPID", pripid);
//        TsHearingReport tsHearingReport = tshearingreportMapper.selectOne(tsHearingReportQueryWrapper);

        //获取法人信息
        LambdaQueryWrapper<EPriPersonCrgs> tasWrapper = new LambdaQueryWrapper<>();
        tasWrapper.eq(EPriPersonCrgs::getPripid, pripid).eq(EPriPersonCrgs::getLerepsign, "1");
        List<EPriPersonCrgs> ePriPersonList = ePriPersonCrgsService.list(tasWrapper);
        EPriPersonCrgs ePriPersonCrgs = ePriPersonList.get(0);

        //获取意见信息
        LambdaQueryWrapper<TSOpinion> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(TSOpinion::getWorkflowid, tsrevtasklist.getWorkflowid())
                .eq(TSOpinion::getOpiniontype, "10")// 经办为0
                .orderByDesc(TSOpinion::getLauptime);
        List<TSOpinion> list = opinionService.list(queryWrapper);


        // 构造ayxx对象（案件信息）
        Map<String, Object> ayxx = new HashMap<>();
        ayxx.put("cBh", UUID.randomUUID().toString().replaceAll("-", "")); // 案件编号
        ayxx.put("aymc", "普通程序案件" + report.getCasename() ); // 案由名称
        ayxx.put("ajmc", "普通程序案件" + report.getCasename() +  BaseDataConstant.REVOKE_CASEREASON_MAP.get(tsCase.getBizEntType()) + "案"); // 案件名称
        ayxx.put("ajmcZywfxw", tsCase.getIllegalActCn()); // 案由描述
        ayxx.put("ayly", "1"); // 案由来源
        ayxx.put("qtlyms", ""); // 其他来源描述
        ayxx.put("sycx", "2"); // 适用程序
        ayxx.put("fxxssj", tsCase.getHandlerDate().format(DateTimeFormatter.ISO_DATE)); // 发现线索时间
        ayxx.put("aynr", report.getCasecon()); // 案源内容
        ayxx.put("aydjrq", tsCase.getRegistTime().format(DateTimeFormatter.ISO_DATE)); // 案源登记日期
        String handlerUserId = tsCase.getHandlerName(); // 假设这个方法获取经办人用户ID
// 2. 构建JSON数组格式的List（服务端期望数组）
        List<String> ayjbrList = new ArrayList<>();
        if (StringUtils.isNotBlank(handlerUserId)) {
            ayjbrList.add(handlerUserId); // 加入用户ID（如："D0915586-E9A0-4CF7-AB47-69FE71CA4CFB"）
        }
        ayxx.put("ayjbr", ayjbrList); // 案源经办人
        ayxx.put("jdcjr", Arrays.asList(tsCase.getHandlerId(), tsCase.getAssistantId())); // 决策层级人
        ayxx.put("ssdw", report.getCasedepname()); // 所属单位
        caseInfo.put("ayxx", ayxx);

        // 构造dsrxx对象（当事人信息）
        List<Map<String, Object>> dsrxxList = new ArrayList<>();
        Map<String, Object> dsrxx = new HashMap<>();
        dsrxx.put("xm", report.getUnitname()); // 姓名
        dsrxx.put("dsrlx", "3"); // 当事人类别
        String lxdh = report.getTel() != null && !report.getTel().trim().isEmpty()
                ? report.getTel().trim()  // 优先取report的电话，去空格
                : (ePriPersonCrgs.getTel() != null && !ePriPersonCrgs.getTel().trim().isEmpty()
                ? ePriPersonCrgs.getTel().trim()  // 其次取ePriPersonCrgs的TEL，去空格
                : ePriPersonCrgs.getMobtel() != null ? ePriPersonCrgs.getMobtel().trim() : "");  // 最后取MOBTEL，无值则为空字符串
        dsrxx.put("lxdh", lxdh);
        // 1. 定义极简的映射关系（一行搞定核心映射）
        Map<String, String> certMap = new HashMap<String, String>() {{
            put("10","1"); put("20","2"); put("30","3"); put("40","20");
            put("51","9"); put("52","10"); put("53","11"); put("54","12");
            put("55","13"); put("56","29"); put("57","15"); put("58","16");
            put("60","4"); put("90","27");
        }};
        // 2. 核心转换+赋值（3行完成）
        String oldType = eBaseinfo.getCertype() == null ? "" : eBaseinfo.getCertype().trim(); // 处理空值/空格
        String newType = certMap.getOrDefault(oldType, "27"); // 转换，默认27
        dsrxx.put("zjlx", newType); // 证件类型
        String sfzjhm = eBaseinfo.getCerno() != null && !eBaseinfo.getCerno().trim().isEmpty()
                ? eBaseinfo.getCerno().trim()  // 优先取eBaseinfo的证件号，去空格
                : (ePriPersonCrgs.getCerno() != null ? ePriPersonCrgs.getCerno().trim() : "");  // 为空则取ePriPersonCrgs的证件号，无值则为空字符串
        dsrxx.put("sfzjhm", sfzjhm);
        dsrxx.put("qtlxfs", ""); // 其他联系方式
        dsrxx.put("dzSheng", ""); // 地址省份
        dsrxx.put("dzShi", ""); // 地址市
        dsrxx.put("dzQu", ""); // 地址区
        dsrxx.put("dz", report.getDom()); // 地址
        String tyshxydm = report.getUniscid() != null && !report.getUniscid().trim().isEmpty()
                ? report.getUniscid().trim()  // 优先取report的统一码，去空格
                : (eBaseinfo.getUniscid() != null ? eBaseinfo.getUniscid().trim() : "");  // 为空则取eBaseinfo的统一码，无值则为空字符串
        dsrxx.put("tyshxydm", tyshxydm);
        dsrxx.put("lxdz", report.getDom());
        dsrxx.put("lxdzSheng", "");
        dsrxx.put("lxdzShi", "");
        dsrxx.put("lxdzQu", "");
        dsrxx.put("ztdm", report.getPripid());
        dsrxx.put("ztzzzzmc", "");
        String fddbr = report.getLerep() != null && !report.getLerep().trim().isEmpty()
                ? report.getLerep().trim()  // 优先取report的法定代表人，去首尾空格
                : (ePriPersonCrgs.getName() != null ? ePriPersonCrgs.getName().trim() : "");  // 为空则取ePriPersonCrgs的姓名，无值则为空字符串
        dsrxx.put("fddbr", fddbr);
        // 补充缺失的参数
        dsrxx.put("sqwt", ""); // 是否授权委托
        dsrxx.put("dlrxm", ""); // 代理人姓名
        dsrxx.put("dlrgzdw", ""); // 代理人工作单位
        dsrxx.put("dlrzjlx", "1"); // 代理人证件类型
        dsrxx.put("dlrzjhm", ""); // 代理人证件号码
        dsrxx.put("dlrlxdh", ""); // 代理人联系电话

        dsrxxList.add(dsrxx);
        caseInfo.put("dsrxx", dsrxxList);

        // 构造ayhcxx对象（案源核查信息）
        Map<String, Object> ayhcxx = new HashMap<>();

        String isRegister = tsCase.getIsRegister();
        ayhcxx.put("hcjl", "1".equals(isRegister) ? "1" : "2");
        ayhcxx.put("ys", "2"); // 验收

        if ("1".equals(isRegister)) {
            ayhcxx.put("ajbh", report.getCaseno()); // 案件编号
            ayhcxx.put("lajg", tsrevtasklists.get(0).getAreaCode()); // 立案机构
            ayhcxx.put("ajmc", "普通程序案件" + report.getCasename());
            ayhcxx.put("zfywly", createUserIdJsonArray(Arrays.asList("1"))); // 执法业务领域
//            ayhcxx.put("chcqkjlaay",tsCase.getSituation()); // 核查期间及立案依据
            ayhcxx.put("wfxwzl",createUserIdJsonArray(Arrays.asList(""))); // 核查期间及立案依据
            ayhcxx.put("zwfxwzl", createUserIdJsonArray(Arrays.asList("0101")));
            Map<String, Object> lawDetail = new HashMap<>();
            lawDetail.put("lawDetailId", illegalact.getIllegactId());
            lawDetail.put("fgmc", "");//没有
            lawDetail.put("title", " ");//没有
            lawDetail.put("content", BaseDataConstant.REVOKE_CASEREASON_MAP.get(tsCase.getBizEntType()));
            List<Map<String, Object>> lawDetailList = new ArrayList<>();
            lawDetailList.add(lawDetail);
            ayhcxx.put("wfflfg", JSON.toJSONString(lawDetailList)); // 违法法律法规模板
            ayhcxx.put("czr", tsCase.getHandlerId()); // 核查经办人
            ayhcxx.put("larq", tsCase.getSetTime().format(DateTimeFormatter.ISO_DATE)); // 立案日期
            // 补充缺失的参数
            ayhcxx.put("hcqkjlaay", tsCase.getSituation()); // 核查期间及立案依据
        }else {
//            ayhcxx.put("chcqkjlaay",tsCase.getSituation()); // 核查期间及立案依据
            ayhcxx.put("zfywly", createUserIdJsonArray(Arrays.asList("1")));
            ayhcxx.put("bylajg",tsrevtasklists.get(0).getAreaCode()); // 立案机构
            // 补充缺失的参数
            ayhcxx.put("hcqkjlaay", tsCase.getSituation()); // 核查期间及立案依据
        }

        caseInfo.put("ayhcxx", ayhcxx);

        // 构造dcqzxx对象（调查取证信息）
        Map<String, Object> dcqzxx = new HashMap<>();
        dcqzxx.put("dccllx", "1");
        dcqzxx.put("dcjsrq", list.get(0).getLauptime().toLocalDate().format(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
        dcqzxx.put("sfjxxzcfgz", "1");
        dcqzxx.put("swbfaj", "2");
        dcqzxx.put("qwmfaj", "2");

        caseInfo.put("dcqzxx", dcqzxx);

        // 构造ajshxx对象（案件审核信息）
        Map<String, Object> ajshxx = new HashMap<>();
        ajshxx.put("shfs", ""); // 审核方式
        ajshxx.put("sfgzdsr", ""); // 是否构成当事人
        ajshxx.put("shrq", ""); // 审核日期
        ajshxx.put("gzrq", ""); // 关注日期

        caseInfo.put("ajshxx", ajshxx);

        // 构造cfgzxx对象（处罚告知信息）
        Map<String, Object> cfgzxx = new HashMap<>();
        cfgzxx.put("sftccsb", tsCase.getIsReviewHearing()); // 是否提出陈述申辩
        cfgzxx.put("sfyqtz", ""); // 是否要求听证
        cfgzxx.put("cssbyj", tsCase.getPleadOpinion()); // 陈述申辩意见
        cfgzxx.put("fhyj", tsCase.getReviewHearingOpinion()); // 复核意见

        // 构造sdxx对象（送达信息）
        Map<String, Object> sdxx = new HashMap<>();
        sdxx.put("cWslb", "");
//        if (tsHearingReport == null) {
//            sdxx.put("cwsmc", "");
//            sdxx.put("csdwswh", "");
//            sdxx.put("dsdrq", "");
//        }else {
//            sdxx.put("cwsmc", tsHearingReport.getArriveWritName());
//            sdxx.put("csdwswh", tsHearingReport.getArriveBackNo());
//            sdxx.put("dsdrq", tsHearingReport.getLaupTime().format(DateTimeFormatter.ISO_DATE));
//        }
        sdxx.put("cwsmc", "");
        sdxx.put("csdwswh", "");
        sdxx.put("dsdrq", "");
        sdxx.put("cSsdr", "");
        sdxx.put("csdSheng", "");
        sdxx.put("csdShi", "");
        sdxx.put("csdQu", "");
        sdxx.put("csdDz", "");
        sdxx.put("nsdfs", 1);
        sdxx.put("csdr", "");
        sdxx.put("csjr", "");
        sdxx.put("cjzr", "");
        sdxx.put("cbz", "");
        sdxx.put("sdhz", "");

        cfgzxx.put("sdxx", sdxx);
        caseInfo.put("cfgzxx", cfgzxx);

        // 构造cfjdxx对象（处罚决定信息）
        Map<String, Object> cfjdxx = new HashMap<>();
        cfjdxx.put("cAjss", report.getIllegfact());
        cfjdxx.put("nSwbfaj", "");
        cfjdxx.put("nQwmfaj", "");

        Map<String, Object> lawDetail = new HashMap<>();
        lawDetail.put("lawDetailId", illegalact.getIllegactId());
        lawDetail.put("fgmc", "");//没有
        lawDetail.put("title", "");//没有
        lawDetail.put("url", "");//没有
        lawDetail.put("content", BaseDataConstant.REVOKE_CASEREASON_MAP.get(tsCase.getBizEntType()));
        List<Map<String, Object>> lawDetailList = new ArrayList<>();
        lawDetailList.add(lawDetail);
        cfjdxx.put("cWfflfg",JSON.toJSONString(lawDetailList));
        cfjdxx.put("cCfyj", report.getPenbasis());
        cfjdxx.put("cZyclsshly", "");
        cfjdxx.put("dCljdrq", report.getPendecissdate().toString());
        cfjdxx.put("cZfry", Arrays.asList(tsCase.getHandlerId()));
        cfjdxx.put("nCqjqczcfsy", "");
        cfjdxx.put("cCfzl", createUserIdJsonArray(Arrays.asList("18")));
        cfjdxx.put("cXzcfnr", "吊销营业执照");
        cfjdxx.put("cTpdx", "");
        cfjdxx.put("cTpsx", "");
        cfjdxx.put("nZltkje", "");
        cfjdxx.put("nSjtpje", "");
        cfjdxx.put("nFkje", report.getRefamoord());
        cfjdxx.put("nMsje", report.getForfam());
        cfjdxx.put("nMswfsdje", "");
        cfjdxx.put("nMswpje", "");
        cfjdxx.put("cMswz", report.getForgoods());
        cfjdxx.put("cXkzmc", "");
        cfjdxx.put("cXkzh", "");
        cfjdxx.put("cDxyyzzh", "");

        cfjdxx.put("nHzje", "");
        cfjdxx.put("nAzje", report.getCaseval());
        cfjdxx.put("nGs", "1");
        cfjdxx.put("cBz", "");
        cfjdxx.put("cZfywly", createUserIdJsonArray(Arrays.asList("1")));
        cfjdxx.put("cCljd", createUserIdJsonArray(Arrays.asList("1")));

        // 构造sdxx对象（送达信息）
        Map<String, Object> cfjdSdxx = new HashMap<>();
        cfjdSdxx.put("cWslb", "");
        cfjdSdxx.put("cwsmc", "");
        cfjdSdxx.put("csdwswh", "");
        cfjdSdxx.put("cSsdr", "");
        cfjdSdxx.put("dsdrq", "");
        cfjdSdxx.put("csdSheng", "");
        cfjdSdxx.put("csdShi", "");
        cfjdSdxx.put("csdQu", "");
        cfjdSdxx.put("csdDz", "");
        cfjdSdxx.put("nsdfs", 1);
        cfjdSdxx.put("csdr", "");
        cfjdSdxx.put("csjr", "");
        cfjdSdxx.put("cjzr", "");
        cfjdSdxx.put("cbz", "");
        cfjdSdxx.put("sdhz", "");

        cfjdxx.put("sdxx", cfjdSdxx);

        // 构造xxgs对象（信息公示）
        Map<String, Object> xxgs = new HashMap<>();
        xxgs.put("dGsrq", 0L);
        xxgs.put("dGsjzrq", 0L);
        xxgs.put("cBz", "");
        xxgs.put("nGszt", 20);
        xxgs.put("nAjqk", 2);

        List<Map<String, Object>> qdgsList = new ArrayList<>();
        Map<String, Object> qdgs1 = new HashMap<>();
        qdgs1.put("cGsqdmc", "国家企业信用信息公示系统");
        qdgs1.put("cGsqdbs", "qyxyxxgsxt_gx");
        qdgs1.put("check", true);
        qdgs1.put("dGsjzrq", 0L);
        qdgsList.add(qdgs1);

        Map<String, Object>[] qdgsArray = qdgsList.toArray(new Map[0]);
        xxgs.put("qdgsList", qdgsArray);
        cfjdxx.put("xxgs", xxgs);

        caseInfo.put("cfjdxx", cfjdxx);

        // 构造cfzx对象（处罚执行信息）
        Map<String, Object> cfzx = new HashMap<>();
        cfzx.put("nZxfs", 0);
        cfzx.put("cJkr", "");
        cfzx.put("nJkfs", 0);
        cfzx.put("dJkrq", 0L);
        cfzx.put("nJkje", 0.0);
        cfzx.put("nZnj", 0.0);
        cfzx.put("cZxqk", "");

        // 7. 执行分期数组（Array，条件必填）：空数组（Array类型不能为空字符串/null）
        List<Map<String, Object>> zxfqsList = new ArrayList<>();
        Map<String, Object>[] zxfqsArray = zxfqsList.toArray(new Map[0]);
        cfzx.put("zxfqs", zxfqsArray);

        caseInfo.put("cfzx", cfzx);

        // 构造jaxx对象（结案信息）
        Map<String, Object> jaxx = new HashMap<>();
        jaxx.put("cJaqx", "");
        jaxx.put("cFmkczqk", "");
        jaxx.put("cFmwzczqk", "");
        jaxx.put("dJarq", 0);
        jaxx.put("cJgsxmlbm", "");

        caseInfo.put("jaxx", jaxx);

        // 构造wsxx对象（文书信息）
        Map<String, Object> wsxx = new HashMap<>();

        // 根据文件名确定文书类型并构造相应对象
        String fileTypeKey = getFileTypeKey(fileName);
//        Map<String, Object> wsItem = createWsItem(fileName, base64Content, report);

        Map<String, Object> wsItem = new HashMap<>();
        wsItem.put("fileName", fileName);
        wsItem.put("fileType", "application/pdf");
        wsItem.put("content", base64Content);
        wsItem.put("wswh", report.getPendecno()); // 文书文号

        // 补充缺失的文书信息参数
        wsxx.put("ajlydjb", createEmptyWsItem()); // 案件来源登记表
        wsxx.put("laspb", createEmptyWsItem()); // 立案审批表
        wsxx.put("ajdczjbg", createEmptyWsItem()); // 案件调查终结报告
        wsxx.put("ajshb", createEmptyWsItem()); // 案件审核表
        wsxx.put("cfgzs", createEmptyWsItem()); // 行政处罚告知书
        wsxx.put("ygsxspbGz", createEmptyWsItem()); // 行政处罚案件有关事项审批表
        wsxx.put("sdhzGz", createEmptyWsItem()); // 送达回证-告知
        wsxx.put("xzcfjds", wsItem); // 行政处罚决定书
        wsxx.put("xzcldjds", createEmptyWsItem()); // 行政处理决定审批表
        wsxx.put("sdhzJd", createEmptyWsItem()); // 送达回证-决定
        wsxx.put("hgjs", createEmptyWsItem()); // 合规建设提示书
        wsxx.put("xzcfjdsTm", createEmptyWsItem()); // 行政处罚决定书（脱敏）
        wsxx.put("jaspb", createEmptyWsItem()); // 结案审批表

        caseInfo.put("wsxx", wsxx);

        // 构造ljgdxx对象（关联对象信息）
        Map<String, Object> ljgdxx = new HashMap<>();
        // 补充缺失的参数
        ljgdxx.put("ljr", ""); // 立卷人
        ljgdxx.put("gdrq", ""); // 归档日期
        ljgdxx.put("gdh", ""); // 归档号
        ljgdxx.put("bgqx", ""); // 保管期限
        ljgdxx.put("qzh", ""); // 全宗号
        ljgdxx.put("mlh", ""); // 目录号
        ljgdxx.put("ajh", ""); // 案卷号
        caseInfo.put("ljgdxx", ljgdxx);


        Map<String, Object> sdxxzz = new HashMap<>();
        sdxxzz.put("cWslb", "");
//        if (tsHearingReport == null) {
//            sdxxzz.put("cwsmc", "");
//            sdxxzz.put("csdwswh", "");
//            sdxxzz.put("dsdrq", "");
//        }else {
//            sdxxzz.put("cwsmc", tsHearingReport.getArriveWritName());
//            sdxxzz.put("csdwswh", tsHearingReport.getArriveBackNo());
//            sdxxzz.put("dsdrq", tsHearingReport.getLaupTime().format(DateTimeFormatter.ISO_DATE));
//        }
        sdxxzz.put("cwsmc", "");
        sdxxzz.put("csdwswh", "");
        sdxxzz.put("dsdrq", "");
        sdxxzz.put("cSsdr", "");
        sdxxzz.put("csdSheng", "");
        sdxxzz.put("csdShi", "");
        sdxxzz.put("csdQu", "");
        sdxxzz.put("csdDz", "");
        sdxxzz.put("nsdfs", 1);
        sdxxzz.put("csdr", "");
        sdxxzz.put("csjr", "");
        sdxxzz.put("cjzr", "");
        sdxxzz.put("cbz", "");
        sdxxzz.put("sdhz", "");

        caseInfo.put("sdxx", sdxxzz);

        return caseInfo;
    }

    /**
     * 创建法律条文详情
     */
    private Map<String, Object> createLawDetail() {
        Map<String, Object> lawDetail = new HashMap<>();
        lawDetail.put("lawDetailId", "fd8d7d1a648a4436bf7ba5de35103fbd");
        lawDetail.put("fgmc", "《中华人民共和国公司法（2023修订）》");
        lawDetail.put("title", " / 第二百五十条");
        lawDetail.put("content", "违反本法规定，虚报注册资本、提交虚假材料或者采取其他欺诈手段隐瞒重要事实取得公司登记的，由公司登记机关责令改正，对虚报注册资本的公司，处以虚报注册资本金额百分之五以上百分之十五以下的罚款；对提交虚假材料或者采取其他欺诈手段隐瞒重要事实的公司，处以五万元以上二百万元以下的罚款；情节严重的，吊销营业执照；对直接负责的主管人员和其他直接责任人员处以三万元以上三十万元以下的罚款。");
        return lawDetail;
    }

    /**
     * 创建文书项
     */
    private Map<String, Object> createWsItem(String fileName, String base64Content, CaseZfReport report) {
        Map<String, Object> wsItem = new HashMap<>();
        wsItem.put("fileName", fileName);
        wsItem.put("fileType", FileUtil.getMimeType(fileName));
        wsItem.put("content", base64Content);
        wsItem.put("wswh", "文号1"); // 文书文号
        return wsItem;
    }

    /**
     * 根据文件名确定文书类型键
     */
    private String getFileTypeKey(String fileName) {
        String lowerFileName = fileName.toLowerCase();
        if (lowerFileName.contains("处罚决定书")) {
            return "xzcfjds";
        } else if (lowerFileName.contains("立案审批表")) {
            return "laspb";
        } else if (lowerFileName.contains("案件调查终结报告")) {
            return "ajdczjbg";
        } else if (lowerFileName.contains("结案审批表")) {
            return "jaspb";
        } else if (lowerFileName.contains("行政处罚告知书")) {
            return "cfgzs";
        } else {
            // 默认类型
            return "other";
        }
    }

    /**
     * 创建用户ID列表的JSON数组字符串
     * @param userIds 用户ID列表
     * @return JSON数组格式的字符串，如：["user_id1", "user_id2"]
     */
    private String createUserIdJsonArray(List<String> userIds) {
        if (userIds == null || userIds.isEmpty()) {
            return "[]";
        }

        StringBuilder sb = new StringBuilder();
        sb.append("[");

        for (int i = 0; i < userIds.size(); i++) {
            if (i > 0) {
                sb.append(",");
            }
            sb.append("\"").append(userIds.get(i)).append("\"");
        }

        sb.append("]");
        return sb.toString();
    }

    /**
     * 创建空的文书项
     */
    private Map<String, Object> createEmptyWsItem() {
        Map<String, Object> wsItem = new HashMap<>();
        wsItem.put("fileName", "");
        wsItem.put("fileType", "");
        wsItem.put("content", "");
        wsItem.put("wswh", null);
        return wsItem;
    }

    /**
     * 更新报告状态
     */
    private void updateReportStatus(String id, String status) {
        try {
            CaseZfReport updateReport = new CaseZfReport();
            updateReport.setId(id);
            updateReport.setIsfy(status);

            int result = caseZfReportMapper.updateById(updateReport);
            if (result > 0) {
                log.debug("更新记录{}状态为：{}", id, status);
            } else {
                log.error("更新记录{}状态失败", id);
            }
        } catch (Exception e) {
            log.error("更新记录{}状态时发生错误", id, e);
        }
    }

    /**
     * 更新报告状态和上传路径
     */
    private void updateReportStatusAndPath(String id, String status, String zfpath) {
        try {
            CaseZfReport updateReport = new CaseZfReport();
            updateReport.setId(id);
            updateReport.setIsfy(status);
            updateReport.setZfpath(zfpath);

            int result = caseZfReportMapper.updateById(updateReport);
            if (result > 0) {
                log.debug("更新记录{}状态为：{}, 上传路径：{}", id, status, zfpath);
            } else {
                log.error("更新记录{}状态和路径失败", id);
            }
        } catch (Exception e) {
            log.error("更新记录{}状态和路径时发生错误", id, e);
        }
    }
}
