package thyyxxk.webserver.service.reports;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import thyyxxk.webserver.config.exception.ExceptionEnum;
import thyyxxk.webserver.dao.his.reports.KeShiShouRuDao;
import thyyxxk.webserver.entity.ResultVo;
import thyyxxk.webserver.entity.datamodify.GetDropdownBox;
import thyyxxk.webserver.utils.ToolExcel;
import thyyxxk.webserver.entity.querydata.KeShiFeiiYongTongJi;
import thyyxxk.webserver.entity.querydata.QueryDrugsAndProjects;
import thyyxxk.webserver.service.PublicServer;
import thyyxxk.webserver.utils.*;

import javax.servlet.http.HttpServletResponse;
import java.util.*;

/**
 * <p>
 * 描述： 各个科室收入的情况
 * </p>
 *
 * @author xc
 * @date 2021-10-19 14:50
 */
@Service
@Slf4j
public class KeShiShouRuServer {

    private final KeShiShouRuDao dao;

    private final PublicServer publicServer;

    public KeShiShouRuServer(KeShiShouRuDao dao, PublicServer publicServer) {
        this.dao = dao;
        this.publicServer = publicServer;
    }

    static class PersonComparator implements Comparator<KeShiFeiiYongTongJi> {

        @Override
        public int compare(KeShiFeiiYongTongJi p1, KeShiFeiiYongTongJi p2) {
            if (p1.getChargeDateString() != null && p2.getChargeDateString() != null) {
                Date o1 = DateUtil.parse(p1.getChargeDateString(), DateUtil.DATE);
                Date o2 = DateUtil.parse(p2.getChargeDateString(), DateUtil.DATE);
                assert o1 != null;
                return o1.compareTo(o2);
            }
            return -1;
        }
    }


    public ResultVo<KeShiFeiiYongTongJi> getKeShouFei(QueryDrugsAndProjects param) {
        if (StringUtil.isBlank(param.getStartTime()) || StringUtil.isBlank(param.getEndTime())) {
            return ResultVoUtil.fail(ExceptionEnum.LOGICAL_ERROR, "开始时间和结束时间为空 ∑(っ°Д°;)っ");
        }

        KeShiFeiiYongTongJi qp = new KeShiFeiiYongTongJi();
        log.info("查询科室收费统计 ==> 执行科室：{},开始{},结束：{}。项目编码：{}，录入人：{}，申请科室：{},总数：{}，当前页：{}，页大小：{}", param.getExecUnitList(), param.getStartTime(), param.getEndTime(), param.getChargeCodeMx(), param.getOpId(), param.getReqDeptCode(), param.getTotal(), param.getCurrentPage(), param.getPageSize());
        List<String> keShiLieBiao = publicServer.getKeShiLieBiaoList(param.getExecUnitList());
        GetDropdownBox renHuanCodeHeCodeRs = new GetDropdownBox();
        if (StringUtil.notBlank(param.getOpId())) {
            renHuanCodeHeCodeRs = dao.huoQuRenYuanDeCodeHeCodeRs(param.getOpId());
        }
        Page<KeShiFeiiYongTongJi> page;
        if (param.getTotal() > 0) {
            page = new Page<>(param.getCurrentPage(), param.getPageSize(), false);
        } else {
            page = new Page<>(param.getCurrentPage(), param.getPageSize());
        }

        QueryWrapper<?> qw = new QueryWrapper<>();

        if (param.getLaiYuan() == 0) {
            qw.ge("charge_date", param.getStartTime());
            qw.le("charge_date", param.getEndTime());
            if (ListUtil.notBlank(keShiLieBiao)) {
                qw.in("a.exec_unit", keShiLieBiao);
            }
            if (StringUtil.notBlank(param.getChargeCodeMx())) {
                qw.eq("a.charge_code_mx", param.getChargeCodeMx());
            }
            if (StringUtil.notBlank(renHuanCodeHeCodeRs.getCode())) {
                qw.eq("a.op_id_code", renHuanCodeHeCodeRs.getCode());
            }
            if (StringUtil.notBlank(param.getReqDeptCode())) {
                qw.eq("a.ward_code", param.getReqDeptCode());
            }

            switch (param.getFenLei()) {
                case 0:
                    qw.groupBy("CONVERT(varchar(100), charge_date, 23)");
                    qp.setData(dao.getZhuYuanFeiYongXiangMuFenLeiV2(page,
                            qw,
                            " CONVERT(varchar(100), charge_date, 23) charge_date_string,"));
                    qp.setTotal(page.getTotal());
                    break;
                case 1:
                    qw.groupBy("op_id_code");
                    qp.setData(dao.getZhuYuanFeiYongXiangMuFenLeiV2(page,
                            qw,
                            "op_id_code,opName = (select rtrim(name) from a_employee_mi where code = op_id_code ),"));
                    qp.setTotal(page.getTotal());
                    break;
                case 2:
                    qw.groupBy("charge_code_mx,serial");
                    qp.setData(dao.getZhuYuanFeiYongXiangMuFenLeiV2(page,
                            qw,
                            "charge_code_mx,charge_code_name =(select dbo.get_charge_name(charge_code_mx, serial)),"));
                    qp.setTotal(page.getTotal());
                    break;
                case 3:
                    if (param.getTotal() == 0) {
                        qp = dao.getKeShiFeiYongZhuYuanTotal(keShiLieBiao, param.getStartTime(), param.getEndTime(), param.getChargeCodeMx(), renHuanCodeHeCodeRs.getCode(), renHuanCodeHeCodeRs.getCodeRs(), param.getReqDeptCode());
                    }
                    qp.setData(dao.getKeShiFeiYongZhuYuan(param.getCurrentPage(), param.getPageSize(), keShiLieBiao, param.getStartTime(), param.getEndTime(), param.getChargeCodeMx(), renHuanCodeHeCodeRs.getCode(), renHuanCodeHeCodeRs.getCodeRs(), param.getReqDeptCode()));

                    break;
                case 4:
                    qw.groupBy("a.ward_code");
                    qp.setData(dao.getZhuYuanFeiYongXiangMuFenLeiV2(page,
                            qw,
                            "a.ward_code,wardCodeName = (select rtrim(name) from zd_unit_code where code = a.ward_code),"));
                    qp.setTotal(page.getTotal());
                    break;
                case 5:
                    qw.groupBy("a.inpatient_no,a.admiss_times");
                    qp.setData(dao.getZhuYuanFeiYongXiangMuFenLeiV2(page,
                            qw,
                            "a.inpatient_no as patient," +
                                    "(select rtrim(name) from a_patient_mi where a.inpatient_no = a_patient_mi.inpatient_no) as patient_name," +
                                    "a.admiss_times as times,"));
                    qp.setTotal(page.getTotal());
                    break;
                default:

                    break;
            }
        } else {
            if (StringUtil.notBlank(param.getStartTime())) {
                qw.ge("confirm_time", param.getStartTime());
                qw.le("confirm_time", param.getEndTime());
            }
            if (ListUtil.notBlank(param.getExecUnitList())) {
                qw.in("exec_dept", param.getExecUnitList());
            }
            if (StringUtil.notBlank(param.getChargeCodeMx())) {
                qw.eq("charge_item_code", param.getChargeCodeMx());
            }
            if (StringUtil.notBlank(param.getCode())) {
                qw.eq("confirm_id", param.getCode());
            }
            if (StringUtil.notBlank(param.getReqDeptCode())) {
                qw.eq("warn_dept", param.getReqDeptCode());
            }

            switch (param.getFenLei()) {
                case 0:
                    qw.groupBy("CONVERT(varchar(100),confirm_time, 23)");
                    qp.setData(dao.getMenZhenFeiYongXiangMuFenLeiV2(
                            page,
                            qw,
                            "CONVERT(varchar(100),confirm_time, 23) as charge_date_string,"
                    ));
                    qp.setTotal(page.getTotal());
                    break;
                case 1:
                    qw.groupBy("confirm_id");
                    qp.setData(
                            dao.getMenZhenFeiYongXiangMuFenLeiV2(page,
                                    qw,
                                    "confirm_id,opName = (select rtrim(name) from a_employee_mi where code = confirm_id),")
                    );
                    qp.setTotal(page.getTotal());
                    break;
                case 2:
                    qw.groupBy("charge_item_code,group_no");
                    qp.setData(
                            dao.getMenZhenFeiYongXiangMuFenLeiV2(page,
                                    qw,
                                    "charge_item_code as charge_code_mx,charge_code_name =(select dbo.get_charge_name(charge_item_code, group_no)),")
                    );
                    qp.setTotal(page.getTotal());
                    break;
                case 3:
                    if (param.getTotal() == 0) {
                        qp = dao.getMenZhenFeiYongTotal(keShiLieBiao, param.getStartTime(), param.getEndTime(), param.getChargeCodeMx(), renHuanCodeHeCodeRs.getCode(), renHuanCodeHeCodeRs.getCodeRs(), param.getReqDeptCode());
                    }
                    qp.setData(dao.getMenZhenFeiYong(param.getCurrentPage(), param.getPageSize(), keShiLieBiao, param.getStartTime(), param.getEndTime(), param.getChargeCodeMx(), renHuanCodeHeCodeRs.getCode(), renHuanCodeHeCodeRs.getCodeRs(), param.getReqDeptCode()));
                    break;
                case 4:
                    qw.groupBy("warn_dept");
                    qp.setData(dao.getMenZhenFeiYongXiangMuFenLeiV2(
                            page,
                            qw,
                            "warn_dept as wardCode,wardCodeName = (select rtrim(name) from zd_unit_code where code = warn_dept),"));
                    qp.setTotal(page.getTotal());
                    break;

                case 5:
                    qw.groupBy("patient_id,times,name");
                    qp.setData(dao.getMenZhenFeiYongXiangMuFenLeiV2(
                            page,
                            qw,
                            "rtrim(patient_id) as patient,times,rtrim(name) as patient_name,"));
                    qp.setTotal(page.getTotal());
                    break;
                default:

                    break;
            }
        }
        return ResultVoUtil.success(qp);
    }

    public void exportExcel(HttpServletResponse response, QueryDrugsAndProjects param) {
        double pageSize = 1000;
        double currentPage = param.getTotal() / pageSize;
        int fenDuan = (int) Math.ceil(currentPage);
        List<KeShiFeiiYongTongJi> keShiFeiiYongTongJisList = new ArrayList<>();
        param.setPageSize(1000);
        for (long i = 0; i < fenDuan; i++) {
            param.setCurrentPage(i + 1);
            keShiFeiiYongTongJisList.addAll(getKeShouFei(param).getData().getData());
        }
        ToolExcel excel = new ToolExcel();

        switch (param.getFenLei()) {
            case 0:
                excel.addTitle("chargeDateString", "收费日期", 21);
                break;
            case 1:
                excel.addTitle("opName", "录入人");
                break;
            case 2:
                excel.addTitle("chargeCodeMx", "项目编码")
                        .addTitle("chargeCodeName", "项目名称", 30);
                break;
            case 3:
                excel.addTitle("patientName", "姓名")
                        .addTitle("patient", "住院号")
                        .addTitle("times", "次数")
                        .addTitle("chargeCodeMx", "项目编码")
                        .addTitle("chargeCodeName", "项目名称", 30)
                        .addTitle("chargeDate", "执行日期", 21)
                        .addTitle("chargeDateString", "收费日期", 21)
                        .addTitle("opName", "录入人")
                        .addTitle("execUnitName", "执行科室")
                        .addTitle("wardCodeName", "申请科室");
                break;
            case 4:
                excel.addTitle("wardCodeName", "申请科室");
                break;
            case 5:
                excel.addTitle("patientName", "姓名")
                        .addTitle("patient", "住院号")
                        .addTitle("times", "次数");
                break;
        }

        excel.addTitle("chargeFee", "金额")
                .addTitle("chargeAmount", "数量")
                .addTitle("source", "来源")
                .exportExcel(keShiFeiiYongTongJisList, response);

    }

}
