package com.saye.hospitalgd.service.datamanager.impl;

import cn.hutool.core.convert.Convert;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.io.IORuntimeException;
import cn.hutool.core.text.csv.CsvData;
import cn.hutool.core.text.csv.CsvReader;
import cn.hutool.core.text.csv.CsvRow;
import cn.hutool.core.text.csv.CsvUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.core.util.XmlUtil;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.http.HttpUtil;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import com.saye.hospitalgd.commons.date.DateDUtil;
import com.saye.hospitalgd.commons.string.StringDUtil;
import com.saye.hospitalgd.entity.BankbillHistory;
import com.saye.hospitalgd.service.datamanager.DataManagerService;
import com.saye.hospitalgd.util.DownloadFtpUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.Cell;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.RequestBody;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;

/**
 * @author Mr.zs
 * @date 2024/12/26
 */
@Service
@Slf4j
public class DataManagerServiceImpl implements DataManagerService {
    private static String grant_type = "client_credential";
    private static String appid = "wx83bc9715be856b14";
    private static String secret = "8b2d3e8cb0e590c9884d2c278519a200";

    /**
     * 获取银行端商户对账数据
     *
     * @param map
     * @return
     */
    public HashMap<Object, Object> getBankDataBySH(@RequestBody HashMap<Object, Object> map) {
        HashMap<Object, Object> responseMap = new HashMap<>();
        String errCode = "0";
        String errMsg = "";

        // 先下载文件
        String host = StringDUtil.changeNullToEmpty(map.get("FTP_HOST"));
        String portStr = StringDUtil.changeNullToEmpty(map.get("FTP_PORT"));
        int port = Integer.parseInt("".equals(portStr) ? "21" : portStr);
        String username = StringDUtil.changeNullToEmpty(map.get("FTP_USER"));
        String password = StringDUtil.changeNullToEmpty(map.get("FTP_PASSWORD"));
        String localPath = StringDUtil.changeNullToEmpty(map.get("LOCAL_PATH"));
        String mch_id = StringDUtil.changeNullToEmpty(map.get("MCH_ID"));
        String ftp_path = StringDUtil.changeNullToEmpty(map.get("FTP_PATH"));
        String ftp_file_name = StringDUtil.changeNullToEmpty(map.get("FTP_FILE_NAME"));
        String bill_table_name = StringDUtil.changeNullToEmpty(map.get("BILL_TABLE_NAME"));
        String thirdConfigId = StringDUtil.changeNullToEmpty(map.get("ID"));
        String trade_date = StringDUtil.changeNullToEmpty(map.get("trade_date"));

        HSSFWorkbook sheets = null;
        try {
            // 下载文件
            boolean b = DownloadFtpUtil.downloadFtpFile(host, username, password, port, ftp_path, localPath, ftp_file_name);
            // 判断是否下载到文件
            if (!b) {
                throw new RuntimeException("没有下载到文件" + ftp_file_name);
            }

            // 判断本地是否有文件
            File file = new File(localPath + "/" + ftp_file_name);
            if (file.exists()) {
                // 存在 开始解析 存入数据库
                FileInputStream fileInputStream = new FileInputStream(localPath + "/" + ftp_file_name);

                sheets = new HSSFWorkbook(fileInputStream);
                HSSFSheet sheet = sheets.getSheetAt(0);
                // 获取sheet中第一行行号
                int firstRowNum = sheet.getFirstRowNum();
                // 获取sheet中最后一行行号
                int lastRowNum = sheet.getLastRowNum();

                List<BankbillHistory> list = new ArrayList<>();

                for (int i = firstRowNum + 3; i <= lastRowNum - 2; i++) {// 因为表格中第一行为说明，第二行为列标题
                    HSSFRow row = sheet.getRow(i);
                    BankbillHistory bankbillHistory = new BankbillHistory();

                    // 清算日期
                    HSSFCell qsrq = row.getCell(0);
                    qsrq.setCellType(Cell.CELL_TYPE_STRING);
                    String qsrqStr = qsrq.getStringCellValue().trim();

                    // 拿第一个字段判断这条记录是否为空 如果为空直接跳出 一般这字段为空就是数据结束了或根本没有
                    // 为合计也跳出
                    if ("".equals(qsrqStr) || "合计".equals(qsrqStr)) {
                        break;
                    }

                    bankbillHistory.setCQsrq(qsrqStr);

                    // 交易日期
                    HSSFCell jyrq = row.getCell(1);
                    String jyrqStr = "";
                    jyrq.setCellType(Cell.CELL_TYPE_NUMERIC);
                    if (HSSFDateUtil.isCellDateFormatted(jyrq)) {
                        Date dateCellValue = jyrq.getDateCellValue();
                        jyrqStr = DateDUtil.DateToStr(DateDUtil.yyyy_MM_dd, dateCellValue);
                    }
                    bankbillHistory.setCJyrq(jyrqStr);

                    if (i == 0) {
                        trade_date = jyrqStr;
                    }

                    // 交易时间
                    HSSFCell jysj = row.getCell(2);
                    jysj.setCellType(Cell.CELL_TYPE_STRING);
                    String jysjStr = jysj.getStringCellValue().trim();
                    bankbillHistory.setCJysj(jysjStr);

                    // 卡号
                    HSSFCell card = row.getCell(3);
                    card.setCellType(Cell.CELL_TYPE_STRING);
                    String khStr = card.getStringCellValue().trim();
                    bankbillHistory.setCCard(khStr);

                    // 交易类型
                    HSSFCell jylx = row.getCell(4);
                    jylx.setCellType(Cell.CELL_TYPE_STRING);
                    String jylxStr = jylx.getStringCellValue().trim();
                    bankbillHistory.setCJylx(jylxStr);

                    // 交易金额
                    HSSFCell jyje = row.getCell(5);
                    jyje.setCellType(Cell.CELL_TYPE_STRING);
                    String jyjeStr = jyje.getStringCellValue().trim();
                    bankbillHistory.setCJyje(jyjeStr);

                    // 终端号
                    HSSFCell zdh = row.getCell(6);
                    zdh.setCellType(Cell.CELL_TYPE_STRING);
                    String zdhStr = zdh.getStringCellValue().trim();
                    bankbillHistory.setCZdh(zdhStr);

                    // 清算金额
                    HSSFCell qsje = row.getCell(7);
                    qsje.setCellType(Cell.CELL_TYPE_STRING);
                    String qsjeStr = qsje.getStringCellValue().trim();
                    bankbillHistory.setCQsje(qsjeStr);

                    // 手续费
                    HSSFCell sxf = row.getCell(8);
                    sxf.setCellType(Cell.CELL_TYPE_STRING);
                    String sxfStr = sxf.getStringCellValue().trim();
                    bankbillHistory.setCSxf(sxfStr);

                    // 参考号
                    HSSFCell ckh = row.getCell(9);
                    ckh.setCellType(Cell.CELL_TYPE_STRING);
                    String ckhStr = ckh.getStringCellValue().trim();
                    bankbillHistory.setCCkh(ckhStr);

                    // 流水号
                    HSSFCell lsh = row.getCell(10);
                    lsh.setCellType(Cell.CELL_TYPE_STRING);
                    String lshStr = lsh.getStringCellValue().trim();
                    bankbillHistory.setCLsh(lshStr);

                    // 卡类型
                    HSSFCell klx = row.getCell(11);
                    klx.setCellType(Cell.CELL_TYPE_STRING);
                    String klxStr = klx.getStringCellValue().trim();
                    bankbillHistory.setCKlx(klxStr);

                    // 商户订单号
                    HSSFCell shddh = row.getCell(12);
                    shddh.setCellType(Cell.CELL_TYPE_STRING);
                    String shddhStr = shddh.getStringCellValue().trim();
                    bankbillHistory.setCShddh(shddhStr);

                    // 支付方式
                    HSSFCell zffs = row.getCell(13);
                    zffs.setCellType(Cell.CELL_TYPE_STRING);
                    String zffsStr = zffs.getStringCellValue().trim();
                    bankbillHistory.setCZffs(zffsStr);

                    // 银商订单号
                    HSSFCell ysddh = row.getCell(14);
                    ysddh.setCellType(Cell.CELL_TYPE_STRING);
                    String ysddhStr = ysddh.getStringCellValue().trim();
                    bankbillHistory.setCYsddh(ysddhStr);

                    // 退货订单号
                    HSSFCell thddh = row.getCell(15);
                    thddh.setCellType(Cell.CELL_TYPE_STRING);
                    String thddhStr = thddh.getStringCellValue().trim();
                    bankbillHistory.setCThddh(thddhStr);

                    // 实际支付金额
                    HSSFCell sjzfje = row.getCell(16);
                    sjzfje.setCellType(Cell.CELL_TYPE_STRING);
                    String sjzfjeStr = sjzfje.getStringCellValue().trim();
                    bankbillHistory.setCSjzfje(sjzfjeStr);

                    // 备注字段
                    HSSFCell bzzd = row.getCell(17);
                    bzzd.setCellType(Cell.CELL_TYPE_STRING);
                    String bzzdStr = bzzd.getStringCellValue().trim();
                    bankbillHistory.setCBzzd(bzzdStr);

                    // 付款附言
                    HSSFCell fkfy = row.getCell(18);
                    fkfy.setCellType(Cell.CELL_TYPE_STRING);
                    String fkfyStr = fkfy.getStringCellValue().trim();
                    bankbillHistory.setCFkfy(fkfyStr);

                    // 钱包优惠金额
                    HSSFCell qbyhje = row.getCell(19);
                    qbyhje.setCellType(Cell.CELL_TYPE_STRING);
                    String qbyhjeStr = qbyhje.getStringCellValue().trim();
                    bankbillHistory.setCQbyhje(qbyhjeStr);

                    // 商户优惠金额
                    HSSFCell shyhje = row.getCell(20);
                    shyhje.setCellType(Cell.CELL_TYPE_STRING);
                    String shyhjeStr = shyhje.getStringCellValue().trim();
                    bankbillHistory.setCShyhje(shyhjeStr);

                    // 发卡行
                    HSSFCell fkh = row.getCell(21);
                    fkh.setCellType(Cell.CELL_TYPE_STRING);
                    String fkhStr = fkh.getStringCellValue().trim();
                    bankbillHistory.setCFkh(fkhStr);

                    // 分店简称
                    HSSFCell fdjc = row.getCell(22);
                    fdjc.setCellType(Cell.CELL_TYPE_STRING);
                    String fdjcStr = fdjc.getStringCellValue().trim();
                    bankbillHistory.setCFdjc(fdjcStr);

                    // 其他优惠金额
                    HSSFCell qtyhje = row.getCell(23);
                    qtyhje.setCellType(Cell.CELL_TYPE_STRING);
                    String qtyhjeStr = qtyhje.getStringCellValue().trim();
                    bankbillHistory.setCQtyhje(qtyhjeStr);


                    // 分期期数
                    HSSFCell fqqs = row.getCell(24);
                    fqqs.setCellType(Cell.CELL_TYPE_STRING);
                    String fqqsStr = fqqs.getStringCellValue().trim();
                    bankbillHistory.setCFqqs(fqqsStr);

                    // 分期手续费
                    HSSFCell fqsxf = row.getCell(25);
                    fqsxf.setCellType(Cell.CELL_TYPE_STRING);
                    String fqsxfStr = fqsxf.getStringCellValue().trim();
                    bankbillHistory.setCFqsxf(fqsxfStr);

                    // 分期服务方
                    HSSFCell fqfwf = row.getCell(26);
                    fqfwf.setCellType(Cell.CELL_TYPE_STRING);
                    String fqfwfStr = fqfwf.getStringCellValue().trim();
                    bankbillHistory.setCFqfwf(fqfwfStr);

                    // 分期付息方
                    HSSFCell fqfxf = row.getCell(27);
                    fqfxf.setCellType(Cell.CELL_TYPE_STRING);
                    String fqfxfStr = fqfxf.getStringCellValue().trim();
                    bankbillHistory.setCFqfxf(fqfxfStr);

                    // 子订单号
                    HSSFCell zddh = row.getCell(28);
                    zddh.setCellType(Cell.CELL_TYPE_STRING);
                    String zddhStr = zddh.getStringCellValue().trim();
                    bankbillHistory.setCZddh(zddhStr);

                    // 表名
                    bankbillHistory.setBillTableName(bill_table_name);

                    list.add(bankbillHistory);
                }

                responseMap.put("list", list);
            } else {
                System.out.println("执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name);

                errCode = "999";
                errMsg = "执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name;
            }
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("执行失败，原因：" + e.getMessage());

            errCode = "999";
            errMsg = "执行失败，原因：" + e.getMessage();

        } finally {
            try {
                if (sheets != null) {
                    sheets.close();
                }
            } catch (Exception ie) {
                ie.printStackTrace();
            }
        }

        responseMap.put("errCode", errCode);
        responseMap.put("errMsg", errMsg);


        return responseMap;
    }

    /**
     * 获取银行端商户POS对账数据
     *
     * @param map
     * @return
     */
    public HashMap<Object, Object> getBankDataBySHPOS(@RequestBody HashMap<Object, Object> map) {
        HashMap<Object, Object> responseMap = new HashMap<>();
        String errCode = "0";
        String errMsg = "";

        // 先下载文件
        String host = StringDUtil.changeNullToEmpty(map.get("FTP_HOST"));
        String portStr = StringDUtil.changeNullToEmpty(map.get("FTP_PORT"));
        int port = Integer.parseInt("".equals(portStr) ? "21" : portStr);
        String username = StringDUtil.changeNullToEmpty(map.get("FTP_USER"));
        String password = StringDUtil.changeNullToEmpty(map.get("FTP_PASSWORD"));
        String localPath = StringDUtil.changeNullToEmpty(map.get("LOCAL_PATH"));
        String mch_id = StringDUtil.changeNullToEmpty(map.get("MCH_ID"));
        String ftp_path = StringDUtil.changeNullToEmpty(map.get("FTP_PATH"));
        String ftp_file_name = StringDUtil.changeNullToEmpty(map.get("FTP_FILE_NAME"));
        String bill_table_name = StringDUtil.changeNullToEmpty(map.get("BILL_TABLE_NAME"));
        String thirdConfigId = StringDUtil.changeNullToEmpty(map.get("ID"));
        String trade_date = StringDUtil.changeNullToEmpty(map.get("trade_date"));


        HSSFWorkbook sheets = null;
        try {
            // 下载文件
            boolean b = DownloadFtpUtil.downloadFtpFile(host, username, password, port, ftp_path, localPath, ftp_file_name);
            // 判断是否下载到文件
            if (!b) {
                throw new RuntimeException("没有下载到文件" + ftp_file_name);
            }

            // 判断本地是否有文件
            File file = new File(localPath + "/" + ftp_file_name);
            if (file.exists()) {
                // 存在 开始解析 存入数据库
                FileInputStream fileInputStream = new FileInputStream(localPath + "/" + ftp_file_name);

                sheets = new HSSFWorkbook(fileInputStream);
                HSSFSheet sheet = sheets.getSheetAt(0);
                // 获取sheet中第一行行号
                int firstRowNum = sheet.getFirstRowNum();
                // 获取sheet中最后一行行号
                int lastRowNum = sheet.getLastRowNum();

                List<BankbillHistory> list = new ArrayList<>();

                for (int i = firstRowNum + 3; i <= lastRowNum - 4; i++) {
                    log.info("正在解析第" + i + "行数据");// 因为表格中第一行为说明，第二行为列标题
                    HSSFRow row = sheet.getRow(i);
                    BankbillHistory bankbillHistory = new BankbillHistory();

                    // 清算日期
                    HSSFCell qsrq = row.getCell(0);
                    qsrq.setCellType(Cell.CELL_TYPE_STRING);
                    String qsrqStr = qsrq.getStringCellValue().trim();

                    // 拿第一个字段判断这条记录是否为空 如果为空直接跳出 一般这字段为空就是数据结束了或根本没有
                    if ("".equals(qsrqStr) || "汇总信息".equals(qsrqStr)) {
                        break;
                    }
                    bankbillHistory.setCQsrq(qsrqStr);

                    // 交易日期
                    HSSFCell jyrq = row.getCell(1);
                    String jyrqStr = "";
                    jyrq.setCellType(Cell.CELL_TYPE_NUMERIC);
                    if (HSSFDateUtil.isCellDateFormatted(jyrq)) {
                        Date dateCellValue = jyrq.getDateCellValue();
                        jyrqStr = DateDUtil.DateToStr(DateDUtil.yyyy_MM_dd, dateCellValue);
                    }
                    bankbillHistory.setCJyrq(jyrqStr);

                    if (i == 0) {
                        trade_date = jyrqStr;
                    }

                    // 交易时间
                    HSSFCell jysj = row.getCell(2);
                    jysj.setCellType(Cell.CELL_TYPE_STRING);
                    String jysjStr = jysj.getStringCellValue().trim();
                    bankbillHistory.setCJysj(jysjStr);

                    // 终端号
                    HSSFCell zdh = row.getCell(3);
                    zdh.setCellType(Cell.CELL_TYPE_STRING);
                    String zdhStr = zdh.getStringCellValue().trim();
                    bankbillHistory.setCZdh(zdhStr);

                    // 卡号
                    HSSFCell card = row.getCell(4);
                    card.setCellType(Cell.CELL_TYPE_STRING);
                    String khStr = card.getStringCellValue().trim();
                    bankbillHistory.setCCard(khStr);

                    // 交易类型
                    HSSFCell jylx = row.getCell(5);
                    jylx.setCellType(Cell.CELL_TYPE_STRING);
                    String jylxStr = jylx.getStringCellValue().trim();
                    bankbillHistory.setCJylx(jylxStr);

                    // 交易金额
                    HSSFCell jyje = row.getCell(6);
                    jyje.setCellType(Cell.CELL_TYPE_STRING);
                    String jyjeStr = jyje.getStringCellValue().trim();
                    log.info("jyjeStr:" + jyjeStr);
                    bankbillHistory.setCJyje(jyjeStr);

                    // 清算金额
                    HSSFCell qsje = row.getCell(7);
                    qsje.setCellType(Cell.CELL_TYPE_STRING);
                    String qsjeStr = qsje.getStringCellValue().trim();
                    bankbillHistory.setCQsje(qsjeStr);

                    // 手续费
                    HSSFCell sxf = row.getCell(8);
                    sxf.setCellType(Cell.CELL_TYPE_STRING);
                    String sxfStr = sxf.getStringCellValue().trim();
                    bankbillHistory.setCSxf(sxfStr);

                    // 参考号
                    HSSFCell ckh = row.getCell(9);
                    ckh.setCellType(Cell.CELL_TYPE_STRING);
                    String ckhStr = ckh.getStringCellValue().trim();
                    bankbillHistory.setCCkh(ckhStr);

                    // 流水号
                    HSSFCell lsh = row.getCell(10);
                    lsh.setCellType(Cell.CELL_TYPE_STRING);
                    String lshStr = lsh.getStringCellValue().trim();
                    bankbillHistory.setCLsh(lshStr);

                    // 卡类型
                    HSSFCell klx = row.getCell(11);
                    klx.setCellType(Cell.CELL_TYPE_STRING);
                    String klxStr = klx.getStringCellValue().trim();
                    bankbillHistory.setCKlx(klxStr);

                    // 发卡行
                    HSSFCell fkh = row.getCell(12);
                    fkh.setCellType(Cell.CELL_TYPE_STRING);
                    String fkhStr = fkh.getStringCellValue().trim();
                    bankbillHistory.setCFkh(fkhStr);

                    // 支付方式
                    HSSFCell zffs = row.getCell(13);
                    zffs.setCellType(Cell.CELL_TYPE_STRING);
                    String zffsStr = zffs.getStringCellValue().trim();
                    bankbillHistory.setCZffs(zffsStr);

                    // 银商订单号
                    HSSFCell ysddh = row.getCell(15);
                    ysddh.setCellType(Cell.CELL_TYPE_STRING);
                    String ysddhStr = ysddh.getStringCellValue().trim();
                    log.info("ysddhStr:" + ysddhStr);
                    bankbillHistory.setCYsddh(ysddhStr);

                    // 商户订单号
                    HSSFCell shddh = row.getCell(16);
                    shddh.setCellType(Cell.CELL_TYPE_STRING);
                    String shddhStr = shddh.getStringCellValue().trim();
                    bankbillHistory.setCShddh(shddhStr);

                    // 备注字段
                    HSSFCell bzzd = row.getCell(18);
                    bzzd.setCellType(Cell.CELL_TYPE_STRING);
                    String bzzdStr = bzzd.getStringCellValue().trim();
                    bankbillHistory.setCBzzd(bzzdStr);

                    // 钱包优惠金额
                    HSSFCell fdmcjj = row.getCell(19);
                    fdmcjj.setCellType(Cell.CELL_TYPE_STRING);
                    String fdmcjjStr = fdmcjj.getStringCellValue().trim();
                    bankbillHistory.setCFdjc(fdmcjjStr);

                    // 表名
                    bankbillHistory.setBillTableName(bill_table_name);

                    list.add(bankbillHistory);
                }
                responseMap.put("list", list);
            } else {
                System.out.println("执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name);

                errCode = "999";
                errMsg = "执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name;
            }
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("执行失败，原因：" + e.getMessage());

            errCode = "999";
            errMsg = "执行失败，原因：" + e.getMessage();

        } finally {
            try {
                if (sheets != null) {
                    sheets.close();
                }
            } catch (Exception ie) {
                ie.printStackTrace();
            }
        }


        responseMap.put("errCode", errCode);
        responseMap.put("errMsg", errMsg);


        return responseMap;
    }

    /**
     * 获取银行端商户银联卡对账数据
     *
     * @param map
     * @return
     */
    public HashMap<Object, Object> getBankDataBySHYLK(@RequestBody HashMap<Object, Object> map) {
        HashMap<Object, Object> responseMap = new HashMap<>();
        String errCode = "0";
        String errMsg = "";

        // 先下载文件
        String host = StringDUtil.changeNullToEmpty(map.get("FTP_HOST"));
        String portStr = StringDUtil.changeNullToEmpty(map.get("FTP_PORT"));
        int port = Integer.parseInt("".equals(portStr) ? "21" : portStr);
        String username = StringDUtil.changeNullToEmpty(map.get("FTP_USER"));
        String password = StringDUtil.changeNullToEmpty(map.get("FTP_PASSWORD"));
        String localPath = StringDUtil.changeNullToEmpty(map.get("LOCAL_PATH"));
        String mch_id = StringDUtil.changeNullToEmpty(map.get("MCH_ID"));
        String ftp_path = StringDUtil.changeNullToEmpty(map.get("FTP_PATH"));
        String ftp_file_name = StringDUtil.changeNullToEmpty(map.get("FTP_FILE_NAME"));
        String bill_table_name = StringDUtil.changeNullToEmpty(map.get("BILL_TABLE_NAME"));
        String thirdConfigId = StringDUtil.changeNullToEmpty(map.get("ID"));
        String trade_date = StringDUtil.changeNullToEmpty(map.get("trade_date"));


        HSSFWorkbook sheets = null;
        try {
            // 下载文件
            boolean b = DownloadFtpUtil.downloadFtpFile(host, username, password, port, ftp_path, localPath, ftp_file_name);
            // 判断是否下载到文件
            if (!b) {
                throw new RuntimeException("没有下载到文件" + ftp_file_name);
            }

            // 判断本地是否有文件
            File file = new File(localPath + "/" + ftp_file_name);
            if (file.exists()) {
                // 存在 开始解析 存入数据库
                FileInputStream fileInputStream = new FileInputStream(localPath + "/" + ftp_file_name);

                sheets = new HSSFWorkbook(fileInputStream);
                HSSFSheet sheet = sheets.getSheetAt(0);
                // 获取sheet中第一行行号
                int firstRowNum = sheet.getFirstRowNum();
                // 获取sheet中最后一行行号
                int lastRowNum = sheet.getLastRowNum();

                List<BankbillHistory> list = new ArrayList<>();

                for (int i = firstRowNum + 3; i <= lastRowNum - 2; i++) {// 因为表格中第一行为说明，第二行为列标题
                    HSSFRow row = sheet.getRow(i);
                    BankbillHistory bankbillHistory = new BankbillHistory();

                    // 清算日期
                    HSSFCell qsrq = row.getCell(0);
                    qsrq.setCellType(Cell.CELL_TYPE_STRING);
                    String qsrqStr = qsrq.getStringCellValue().trim();

                    // 拿第一个字段判断这条记录是否为空 如果为空直接跳出 一般这字段为空就是数据结束了或根本没有
                    if ("".equals(qsrqStr) || "合计".equals(qsrqStr)) {
                        break;
                    }
                    bankbillHistory.setCQsrq(qsrqStr);

                    // 交易日期
                    HSSFCell jyrq = row.getCell(1);
                    String jyrqStr = "";
                    jyrq.setCellType(Cell.CELL_TYPE_NUMERIC);
                    if (HSSFDateUtil.isCellDateFormatted(jyrq)) {
                        Date dateCellValue = jyrq.getDateCellValue();
                        jyrqStr = DateDUtil.DateToStr(DateDUtil.yyyy_MM_dd, dateCellValue);
                    }
                    bankbillHistory.setCJyrq(jyrqStr);

                    if (i == 0) {
                        trade_date = jyrqStr;
                    }

                    // 交易时间
                    HSSFCell jysj = row.getCell(2);
                    jysj.setCellType(Cell.CELL_TYPE_STRING);
                    String jysjStr = jysj.getStringCellValue().trim();
                    bankbillHistory.setCJysj(jysjStr);

                    // 终端号
                    HSSFCell zdh = row.getCell(3);
                    zdh.setCellType(Cell.CELL_TYPE_STRING);
                    String zdhStr = zdh.getStringCellValue().trim();
                    bankbillHistory.setCZdh(zdhStr);

                    // 卡号
                    HSSFCell card = row.getCell(4);
                    card.setCellType(Cell.CELL_TYPE_STRING);
                    String khStr = card.getStringCellValue().trim();
                    bankbillHistory.setCCard(khStr);

                    // 交易类型
                    HSSFCell jylx = row.getCell(5);
                    jylx.setCellType(Cell.CELL_TYPE_STRING);
                    String jylxStr = jylx.getStringCellValue().trim();
                    bankbillHistory.setCJylx(jylxStr);

                    // 交易金额
                    HSSFCell jyje = row.getCell(6);
                    jyje.setCellType(Cell.CELL_TYPE_STRING);
                    String jyjeStr = jyje.getStringCellValue().trim();
                    bankbillHistory.setCJyje(jyjeStr);

                    // 清算金额
                    HSSFCell qsje = row.getCell(7);
                    qsje.setCellType(Cell.CELL_TYPE_STRING);
                    String qsjeStr = qsje.getStringCellValue().trim();
                    bankbillHistory.setCQsje(qsjeStr);

                    // 手续费
                    HSSFCell sxf = row.getCell(8);
                    sxf.setCellType(Cell.CELL_TYPE_STRING);
                    String sxfStr = sxf.getStringCellValue().trim();
                    bankbillHistory.setCSxf(sxfStr);

                    // 流水号
                    HSSFCell lsh = row.getCell(9);
                    lsh.setCellType(Cell.CELL_TYPE_STRING);
                    String lshStr = lsh.getStringCellValue().trim();
                    bankbillHistory.setCLsh(lshStr);

                    // 卡类型
                    HSSFCell klx = row.getCell(10);
                    klx.setCellType(Cell.CELL_TYPE_STRING);
                    String klxStr = klx.getStringCellValue().trim();
                    bankbillHistory.setCKlx(klxStr);

                    // 发卡行
                    HSSFCell fkh = row.getCell(11);
                    fkh.setCellType(Cell.CELL_TYPE_STRING);
                    String fkhStr = fkh.getStringCellValue().trim();
                    bankbillHistory.setCFkh(fkhStr);

                    // 系统参考号 （对应银商订单号）
                    HSSFCell xtckh = row.getCell(12);
                    xtckh.setCellType(Cell.CELL_TYPE_STRING);
                    String xtckhStr = xtckh.getStringCellValue().trim();

                    // 支付方式
                    bankbillHistory.setCZffs("银行卡支付");

                    // 银商订单号
                    bankbillHistory.setCYsddh(xtckhStr);

                    // 表名
                    bankbillHistory.setBillTableName(bill_table_name);

                    list.add(bankbillHistory);
                }
                responseMap.put("list", list);
            } else {
                System.out.println("执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name);

                errCode = "999";
                errMsg = "执行失败，原因：路径" + ftp_path + "下无下载文件" + ftp_file_name;
            }
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("执行失败，原因：" + e.getMessage());

            errCode = "999";
            errMsg = "执行失败，原因：" + e.getMessage();

        } finally {
            try {
                if (sheets != null) {
                    sheets.close();
                }
            } catch (Exception ie) {
                ie.printStackTrace();
            }
        }
        responseMap.put("errCode", errCode);
        responseMap.put("errMsg", errMsg);
        return responseMap;
    }

    /**
     * 获取微信支付对账数据
     *
     * @param map
     * @return
     */
    public HashMap<Object, Object> getBankDataByWXAPI(@RequestBody HashMap<Object, Object> map) {
        List<BankbillHistory> list = new ArrayList<>();
        log.info("开始获取微信账单");
        HashMap<Object, Object> responseMap = new HashMap<>();
        String errCode = "0";
        String errMsg = "";

        String localPath = StringDUtil.changeNullToEmpty(map.get("LOCAL_PATH"));
        String mch_id = StringDUtil.changeNullToEmpty(map.get("MCH_ID"));
        String trade_date = StringDUtil.changeNullToEmpty(map.get("trade_date"));

        HashMap<String, Object> reqMap = new HashMap<>();
        reqMap.put("grant_type", grant_type);
        reqMap.put("appid", appid);
        reqMap.put("secret", secret);

        String randomStr = RandomUtil.randomString(32);

        String signString = "appid=" + appid + "&bill_date=" + trade_date + "&bill_type=ALL&mch_id=" + mch_id + "&nonce_str=" + randomStr + "&key=9b996ad13a7d11ee8c2b000c29686702";
        String sign = SecureUtil.md5(signString).toUpperCase();
        String reqXml = "<xml>\n" +
                "  <appid>" + appid + "</appid>\n" +
                "  <bill_date>" + trade_date + "</bill_date>\n" +
                "  <bill_type>ALL</bill_type>\n" +
                "  <mch_id>" + mch_id + "</mch_id>\n" +
                "  <nonce_str>" + randomStr + "</nonce_str>\n" +
                "  <sign>" + sign + "</sign>\n" +
                "</xml>";
        // 获取access_token
        String body1 = HttpUtil.createPost("https://api.mch.weixin.qq.com/pay/downloadbill").header("Content-Type", "text/xml").body(reqXml).execute().body();
        String[] split = body1.split("\n");
        for (int i = 1; i < split.length - 2; i++) {
            String[] split1 = split[i].split(",");
            BankbillHistory bankbillHistory = new BankbillHistory();
            int flag = 0;
            for (int j = 0; j < split1.length; j++) {
                if (j == 0) {
                    String s = split1[j].replaceAll("`", "");
                    String[] split2 = s.split(" ");
                    bankbillHistory.setCQsrq(split2[0]);
                    bankbillHistory.setCJyrq(split2[0]);
                    bankbillHistory.setCJysj(split2[1]);
                }
                if (j == 1) {
                    String s = split1[j].replaceAll("`", "");
                    bankbillHistory.setCZdh(s);
                }
                if (j == 2) {
                    String s = split1[j].replaceAll("`", "");
                    bankbillHistory.setCCkh(s);
                }
                if (j == 5) {
                    String s = split1[j].replaceAll("`", "");
                    bankbillHistory.setCYsddh(s);
                }
                if (j == 6) {
                    String s = split1[j].replaceAll("`", "");
                    bankbillHistory.setCShddh(s);
                }
                if (j == 7) {
                    String s = split1[j].replaceAll("`", "");
                    bankbillHistory.setCCard(s);
                }
                if (j == 9) {
                    String s = split1[j].replaceAll("`", "");
                    if (s.equals("REFUND")) {
                        flag = -1;
                    }
                }
                if (j == 21) {
                    String s = split1[j].replaceAll("`", "");
                    String s1 = s.replaceAll(" ", ",").replaceAll("\\\\", "");
                    JSONObject entries = JSONUtil.parseObj(s1);
                    Object zfje = entries.get("zfje");
                    if (flag < 0) {
                        bankbillHistory.setCJyje("-" + Convert.toDouble(zfje));
                    } else {
                        bankbillHistory.setCJyje(Convert.toDouble(zfje).toString());
                    }
                }
                bankbillHistory.setBillTableName("微信支付账单");
            }
            list.add(bankbillHistory);
        }
        // 获取access_token
        String body = HttpUtil.createPost("https://api.weixin.qq.com/cgi-bin/stable_token").body(JSONUtil.toJsonStr(reqMap)).execute().body();

        String access_token = JSONUtil.parseObj(body).getStr("access_token");
        // 获取医保账单下载地址
        // https://api.weixin.qq.com/payinsurance/billdownload?access_token=ACCESS_TOKEN
        String signYBString = "appid=" + appid + "&bill_date=" + trade_date + "&bill_type=ALL&mch_id=" + mch_id + "&nonce_str=" + randomStr + "&key=f6d394fbc881fee73172232a08dc9c03";
        String signYB = SecureUtil.md5(signYBString).toUpperCase();
        String reqYbXml = "<xml>\n" +
                "  <appid>" + appid + "</appid>\n" +
                "  <bill_date>" + trade_date + "</bill_date>\n" +
                "  <bill_type>ALL</bill_type>\n" +
                "  <mch_id>" + mch_id + "</mch_id>\n" +
                "  <nonce_str>" + randomStr + "</nonce_str>\n" +
                "  <sign>" + signYB + "</sign>\n" +
                "</xml>";
        String resBody = HttpUtil.createPost("https://api.weixin.qq.com/payinsurance/billdownload?access_token=" + access_token).header("Content-Type", "text/xml").body(reqYbXml).execute().body();
        Document document = XmlUtil.parseXml(resBody);
        Element elementG = XmlUtil.getRootElement(document);
        Element returnCode = XmlUtil.getElement(elementG, "return_code");
        if (returnCode.getTextContent().equals("SUCCESS")) {// 响应成功
            // 下载文件
            Element downloadUrl = XmlUtil.getElement(elementG, "download_url");
            String dwUrl = downloadUrl.getTextContent();
            log.info("开始下载文件");
            HttpUtil.downloadFileFromUrl(dwUrl, localPath + File.separator + trade_date + ".csv");
            HttpUtil.downloadFileFromUrl(dwUrl, localPath + File.separator + trade_date + ".txt");
            // HttpUtil.downloadFileFromUrl(dwUrl, localPath);
            log.info("下载文件成功");
            CsvReader reader = CsvUtil.getReader();
            try {

                CsvData read = reader.read(FileUtil.file(localPath + File.separator + trade_date + ".csv"));
                List<CsvRow> rows = read.getRows();

                for (int i = 1; i < rows.size(); i++) {
                    CsvRow row = rows.get(i);
                    BankbillHistory bankbillHistory = new BankbillHistory();
                    String s = row.get(0).replaceAll("`", "");
                    String[] s1 = s.split(" ");
                    bankbillHistory.setCJyrq(s1[0]);
                    bankbillHistory.setCQsrq(s1[0]);
                    bankbillHistory.setCJysj(s1[1]);
                    bankbillHistory.setCZdh(row.get(1).replaceAll("`", ""));
                    bankbillHistory.setCCkh(row.get(2).replaceAll("`", ""));
                    bankbillHistory.setCLsh(row.get(5).replaceAll("`", ""));
                    bankbillHistory.setCShddh(row.get(6).replaceAll("`", ""));
                    bankbillHistory.setCCard(row.get(7).replaceAll("`", ""));
                    bankbillHistory.setCYsddh(row.get(25).replaceAll("`", ""));
                    if (row.get(46).replaceAll("`", "").equals("0.00")) {
                        continue;
                    }
                    if (row.get(45).replaceAll("`", "").equals("REFUND")) {
                        bankbillHistory.setCJyje("-" + row.get(46).replaceAll("`", ""));
                    } else {
                        bankbillHistory.setCJyje(row.get(46).replaceAll("`", ""));
                    }
                    bankbillHistory.setBillTableName("微信支付账单");
                    list.add(bankbillHistory);
                }
                responseMap.put("list", list);
            } catch (IORuntimeException e) {
                throw new RuntimeException(e);
            } finally {
                try {
                    reader.close();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            }
        } else {
            // 返回响应结果
            Element returnMsg = XmlUtil.getElement(elementG, "return_msg");
            errCode = "999";
            errMsg = returnMsg.getTextContent();
        }
        responseMap.put("errCode", errCode);
        responseMap.put("errMsg", errMsg);
        return responseMap;
    }
}
