package com.lantone.qc.kernel.catalogue.dutyshiftsystem;

import com.lantone.qc.kernel.catalogue.QCCatalogue;
import com.lantone.qc.kernel.util.CatalogueUtil;
import com.lantone.qc.pub.model.InputInfo;
import com.lantone.qc.pub.model.OutputInfo;
import com.lantone.qc.pub.model.doc.LeaveHospitalDoc;
import com.lantone.qc.pub.model.doc.StagesSummaryDoc;
import com.lantone.qc.pub.model.doc.transferrecord.TransferRecordDoc;
import com.lantone.qc.pub.util.StringUtil;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * @ClassName : DUT0296
 * @Description : 无阶段小结
 * 住院时间超过1个月需要阶段小结， 出院时间和入院时间做比较，超过一个月查找阶段小结
 * 住院30天患者需写“阶段小结”，但在住院期间转科的患者，时间应该是从转科那天算起。
 * @Author : 楼辉荣
 * @Date: 2020-03-06 17:28
 */
@Component
public class DUT0296 extends QCCatalogue {
    public void start(InputInfo inputInfo, OutputInfo outputInfo) {
        status.set("0");
        LeaveHospitalDoc leaveHospitalDoc = inputInfo.getLeaveHospitalDoc();
        if (leaveHospitalDoc == null) {
            return;
        }

        List<StagesSummaryDoc> stagesSummaryDocs = inputInfo.getStagesSummaryDocs();
        TransferRecordDoc transferRecordDoc = inputInfo.getTransferRecordDocs();//转科记录

        Map<String, String> structureMap_leave = leaveHospitalDoc.getStructureMap();
        String beDate = structureMap_leave.get("入院时间"); //2019-12-07 08:48
        String leaveDate = structureMap_leave.get("出院时间");//2019-12-10 10:49
        /* 住院天数小于30天不报错*/
        int lengthOfStayNum = 0;
        if (StringUtil.isNotBlank(beDate) && StringUtil.isNotBlank(leaveDate)) {
            lengthOfStayNum = dateDifference(beDate, leaveDate);
            if (lengthOfStayNum < 30) {
                return;
            }
        }
        lengthOfStayNum = getLengthOfStay(structureMap_leave);
        if (lengthOfStayNum < 30) {
            return;
        }


        if (transferRecordDoc != null) {
            List<TransferRecordDoc> allTransferDocs = transferRecordDoc.getAllTransferDocs();
            String firstOutRecordDate = getFirstOutRecordDate(allTransferDocs);
            if (StringUtil.isNotBlank(firstOutRecordDate) && StringUtil.isNotBlank(beDate)) {
                //入院时间到第一次转出时间，大于30天则报错
                int dateDifference = dateDifference(beDate, firstOutRecordDate);
                if (dateDifference > 30 && (stagesSummaryDocs == null || stagesSummaryDocs.size() == 0)) {
                    status.set("-1");
                    return;
                }
            }
            String lastInrecordDate = getLastInrecordDate(allTransferDocs);
            if (StringUtil.isNotBlank(lastInrecordDate) && StringUtil.isNotBlank(leaveDate)) {
                //最后一次转入时间到出院时间，大于30天则报错
                int dateDifference = dateDifference(lastInrecordDate, leaveDate);
                if (dateDifference > 30 && (stagesSummaryDocs == null || stagesSummaryDocs.size() == 0)) {
                    status.set("-1");
                    return;
                }
            }
            List<String> allRecordPairs = getAllRecordPairs(allTransferDocs);
            for (String recordPair : allRecordPairs) {
                String[] recordPairSplit = recordPair.split(",");
                int dateDifference = dateDifference(recordPairSplit[0], recordPairSplit[1]);
                if (dateDifference > 30 && (stagesSummaryDocs == null || stagesSummaryDocs.size() == 0)) {
                    status.set("-1");
                    return;
                }
            }
        } else {
            //没有转科记录，直接入院时间和出院时间比
            if (StringUtil.isNotBlank(beDate) && StringUtil.isNotBlank(leaveDate)) {
                int dateDifference = dateDifference(beDate, leaveDate);
                if (dateDifference > 30 && (stagesSummaryDocs == null || stagesSummaryDocs.size() == 0)) {
                    status.set("-1");
                }
                if (checkDays(stagesSummaryDocs, dateDifference)) {
                    status.set("-1");
                    return;
                }
            }

            int lengthOfStay = getLengthOfStay(structureMap_leave);
            if (checkDays(stagesSummaryDocs, lengthOfStay)) {
                status.set("-1");
            }
        }

    }

    private int getLengthOfStay(Map<String, String> structureMap_leave) {
        int lengthOfStayNum = 0;
        String lengthOfStay = structureMap_leave.get("住院天数");
        if (StringUtil.isNotBlank(lengthOfStay)) {
            lengthOfStayNum = onlyNum(lengthOfStay);
        }
        return lengthOfStayNum;
    }

    private boolean checkDays(List<StagesSummaryDoc> stagesSummaryDocs, int dateDifference) {
        if (stagesSummaryDocs != null && stagesSummaryDocs.size() > 0) {
            double sum = Math.floor(dateDifference / 30);
            return sum != stagesSummaryDocs.size();
        }
        return true;
    }

    /**
     * 获取第一条转出记录时间
     *
     * @param allTransferDocs
     * @return
     */
    private String getFirstOutRecordDate(List<TransferRecordDoc> allTransferDocs) {
        for (TransferRecordDoc transferDoc : allTransferDocs) {
            Map<String, String> structureMap = transferDoc.getStructureMap();
            String outDepartment = structureMap.get("转出科室");
            if (StringUtil.isBlank(outDepartment)) {
                //如果转出科室为空，则为转出记录
                return structureMap.get("转科日期");
            }
        }
        return null;
    }

    /**
     * 获取最后一条转入记录
     *
     * @param allTransferDocs
     * @return
     */
    private String getLastInrecordDate(List<TransferRecordDoc> allTransferDocs) {
        for (int i = allTransferDocs.size() - 1; i > 0; i--) {
            Map<String, String> structureMap = allTransferDocs.get(i).getStructureMap();
            String outDepartment = structureMap.get("转出科室");
            if (StringUtil.isNotBlank(outDepartment)) {
                //如果转出科室不为空，则为转入记录
                return structureMap.get("转科日期");
            }
        }
        return null;
    }

    /**
     * 获取所有转入时间-转出时间 pair
     *
     * @param allTransferDocs
     * @return
     */
    private List<String> getAllRecordPairs(List<TransferRecordDoc> allTransferDocs) {
        List<String> allRecordPairs = new ArrayList<>();
        for (int i = 0; i < allTransferDocs.size(); i++) {
            Map<String, String> structureMap = allTransferDocs.get(i).getStructureMap();
            String outDepartment = structureMap.get("转出科室");
            if (StringUtil.isNotBlank(outDepartment)) {
                //如果转出科室不为空，则为转入记录
                String transferDateInStr = structureMap.get("转科日期");
                if (i + 1 < allTransferDocs.size()) {
                    //如果转入记录下一条是转出记录
                    Map<String, String> nextStructureMap = allTransferDocs.get(i + 1).getStructureMap();
                    if (StringUtil.isBlank(nextStructureMap.get("转出科室"))) {
                        //如果转出科室为空，则为转出记录
                        String transferDateOutStr = nextStructureMap.get("转科日期");
                        allRecordPairs.add(transferDateInStr + "," + transferDateOutStr);
                    }
                }
            }
        }
        return allRecordPairs;
    }

    private int dateDifference(String beDate, String leaveDate) {
        int day = 0;
        try {
            Date dateIn = StringUtil.parseDateTime(beDate);
            Date dateOut = StringUtil.parseDateTime(leaveDate);
            if (dateIn == null || dateOut == null) return 0;
            Calendar from = Calendar.getInstance();
            from.setTime(dateIn);
            Calendar to = Calendar.getInstance();
            to.setTime(dateOut);
            long timeS,timeE,timeDiff = 0;
            try {
                timeS = from.getTimeInMillis();
                timeE = to.getTimeInMillis();
                timeDiff = (timeE - timeS) / (1000 * 60* 60 * 24);
            } catch (Exception e) {
                e.printStackTrace();
            }
            day = (int) timeDiff;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return day;
    }

    private int onlyNum(String str) {
        return Integer.parseInt(str.replaceAll("[^0-9]", ""));
    }
}