package com.sys.bus.jx.service;

import com.jfinal.aop.Before;
import com.jfinal.aop.Enhancer;
import com.jfinal.plugin.activerecord.Db;
import com.jfinal.plugin.activerecord.Record;
import com.jfinal.plugin.activerecord.SqlPara;
import com.jfinal.plugin.activerecord.tx.Tx;
import com.sys.bus.hr.model.Dept;
import com.sys.bus.hr.model.Person;
import com.sys.bus.hr.service.HrService;
import com.sys.bus.model.*;
import com.sys.bus.sys.wx.WxMsgType;
import com.sys.core.model.DataBean;
import com.sys.core.utils.Conditions;
import com.sys.core.utils.Tool;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.*;
import java.util.stream.Collectors;

public class JxCommonService {
    static OrgService orgService = Enhancer.enhance(OrgService.class);
    static HrService hrService = Enhancer.enhance(HrService.class);
    static KpilibService kpilibService = Enhancer.enhance(KpilibService.class);
    static JxCycleService jxCycleService = Enhancer.enhance(JxCycleService.class);
    //static RatingService ratingService = Enhancer.enhance(RatingService.class);

    static WflogService wflogService = Enhancer.enhance(WflogService.class);
    static PersonManagerService personManagerService = Enhancer.enhance(PersonManagerService.class);
    static MailService mailService = new MailService();
    static WxMsgService wxMsgService = new WxMsgService();
    Log log = LogFactory.getLog(this.getClass());

    public Entry getJxentryById(String entryid) {
        return Entry.dao.findById(entryid);
    }

    public Boolean getPermission(String entryCycleid, String entryOrgid) {
        UpdateRatingPermission sqlParam = new UpdateRatingPermission();
        sqlParam.setCycleId(entryCycleid);
        Conditions condi = new Conditions();
        condi.modelToCondition(sqlParam);
        SqlPara sp = condi.getSqlPara();
        sp.setSql(sp.getSql());
        List<UpdateRatingPermission> updateRatingPermissions = UpdateRatingPermission.dao.find(sp);
        if (updateRatingPermissions.size() > 0) {
            List<Dept> depts = Dept.dao.find("SELECT\n" +
                    "\tfid id,\n" +
                    "\tfname_l2 name,\n" +
                    "\tfdisplayname_l2 longname,\n" +
                    "\tfLongNumber longnumber,\n" +
                    "\tfparentid parentId,\n" +
                    "\tflevel \n" +
                    "FROM\n" +
                    "\tt_org_admin a \n" +
                    "WHERE\n" +
                    "\ta.FISSEALUP = 0 \n and a.FID = '" + entryOrgid + "'" +
                    "ORDER BY\n" +
                    "\tflevel");
            if (depts.size() <= 0) {
                return false;
            }
            Dept dept = depts.get(0);
            for (UpdateRatingPermission updateRatingPermission : updateRatingPermissions) {
                String isSubordinate = updateRatingPermission.getIsSubordinate();//是否包含下级组织
                List<Dept> depts1 = Dept.dao.find("SELECT\n" +
                        "\tfid id,\n" +
                        "\tfname_l2 name,\n" +
                        "\tfdisplayname_l2 longname,\n" +
                        "\tfLongNumber longnumber,\n" +
                        "\tfparentid parentId,\n" +
                        "\tflevel \n" +
                        "FROM\n" +
                        "\tt_org_admin a \n" +
                        "WHERE\n" +
                        "\ta.FISSEALUP = 0 \n and a.FID = '" + updateRatingPermission.getOrgId() + "'" +
                        "ORDER BY\n" +
                        "\tflevel");
                if (depts1.size() <= 0) {
                    continue;
                }
                Dept dept1 = depts1.get(0);
                String longNumber = dept1.getLongNumber();
                if (isSubordinate.equals("1")) {
                    if (dept.getLongNumber().startsWith(longNumber)) {
                        return true;
                    }
                }else if (isSubordinate.equals("0")) {
                    if (longNumber.equals(dept.getLongNumber())) {
                        return true;
                    }
                }

            }
        }
        return false;
    }

    public void setEntryDisplayName(Entry entry) {
        String entryDisplayName = entry.getEntryDisplayname();
        if (entryDisplayName.startsWith("刀锋集团_刀锋互娱_")) {
            entryDisplayName = entryDisplayName.substring("刀锋集团_刀锋互娱_".length());
        }
        if (entryDisplayName.startsWith("刀锋集团_")) {
            entryDisplayName = entryDisplayName.substring("刀锋集团_".length());
        }
        if (entryDisplayName.length() <= entryDisplayName.replace("_", "").length() + 1) {
            entry.setEntryDisplayname(entryDisplayName);
            return;
        }
        int index = entryDisplayName.indexOf("_");
        index = entryDisplayName.indexOf("_", index + 1);
        entry.setEntryDisplayname(entryDisplayName.substring(0, index));

    }

    public Entry getJxentryByIdAndAttachment(String entryId) {
        return Entry.dao.findFirst("select e.*,(select count(*) from ct_jx_attachment where attachment_entryid =entry_id) attachmentCnt  from ct_jx_entry e where entry_id=?", entryId);
    }

    public EntryNo getEntryNoById(String entryNoId) {
        return EntryNo.dao.findById(entryNoId);
    }

    /**
     * 根据批次号判断该批次所有数据是否已经评级完后
     *
     * @param entryNO
     * @return
     */
    public boolean isRatingOver(String entryNO) {
        String sql = "select * from ct_jx_ratingentry where ratingentry_entryno = ? and ratingentry_appnode <> '9'";
        List<Record> records = Db.find(sql, entryNO);
        return records.size() <= 0;
    }

    /**
     * 更新人员定级数据状态
     *
     * @param entryNO
     * @param appNode
     */
    public int updateRatingEntryAppNode(String entryNO, String appNode) {
        String sql = " update ct_jx_ratingentry set ratingentry_appnode = ?,ratingentry_apptime=? where ratingentry_entryno = ?";
        return Db.update(sql, appNode, Tool.getCurrTime(), entryNO);

    }

    public EntryNo getEntryNoByOrgAndCycle(String orgId, String cycleId) {
        EntryNo eno = new EntryNo();
        eno.setEntrynoOrgid(orgId);
        eno.setEntrynoCycleid(cycleId);
        Conditions condi = new Conditions();
        condi.modelToCondition(eno);
        SqlPara sp = condi.getSqlPara();
        List<EntryNo> entryNos = EntryNo.dao.find(sp);
        return entryNos.size() > 0 ? entryNos.get(0) : null;
    }

    public EntryNo getEntryNoByKpiId(String kpiId) {
        List<EntryNo> list = EntryNo.dao.find("select * from ct_jx_entryno eno left join ct_jx_entry en on eno.entryno_id = en.entry_no left join ct_jx_kpi k on  k.kpi_entryid=en.entry_id where k.kpi_id=?", kpiId);
        if (list.size() == 1) {
            return list.get(0);
        }
        return null;
    }

    public EntryNo getEntryNoByEntryId(String entryId) {
        List<EntryNo> list = EntryNo.dao.find("select * from ct_jx_entryno eno left join ct_jx_entry en on eno.entryno_id = en.entry_no where en.entry_id=?", entryId);
        if (list.size() == 1) {
            return list.get(0);
        }
        return null;
    }

    public EntryNo getEntryNoByRatingId(String ratingId) {
        List<EntryNo> list = EntryNo.dao.find("select * from ct_jx_entryno eno left join ct_jx_ratingentry en on eno.entryno_id = en.ratingentry_entryno where en.ratingentry_id=?", ratingId);
        if (list.size() == 1) {
            return list.get(0);
        }
        return null;
    }

    public EntryNo getEntryNoByRatingDeptId(String ratingDeptId) {
        List<EntryNo> list = EntryNo.dao.find("select * from ct_jx_entryno eno left join ct_jx_ratingentry en on eno.entryno_id = en.ratingentry_entryno left join ct_jx_ratingdept de on  (en.ratingentry_deptid= de.ratingdept_id or en.ratingentry_centerid= de.ratingdept_id)where de.ratingdept_id=?", ratingDeptId);
        if (list.size() > 0) {
            return list.get(0);
        }
        return null;
    }


    @Before(Tx.class)
    public DataBean importRatingData(List<Map<String, Object>> dataList, String entryNo, Person operator, boolean isJxjl, boolean isAdmin) {
        String pid = operator.getId();

        if (dataList == null || dataList.size() < 2) {
            return exceptionReturn("缺少数据！");
        }
        Map<String, Entry> personName2Entry = new HashMap();
        String[] titles = {"序号", "被考核人", "评级结果"};

        Map<String, Object> titleMap = dataList.get(0);
        Map<String, String> tmap = new HashMap<String, String>();//表头-FX 映射
        for (String s : titleMap.keySet()) {
            tmap.put(titleMap.get(s).toString().trim(), s);
        }
        for (String title : titles) {
            if (!tmap.containsKey(title)) {
                return exceptionReturn("缺少列<" + title + ">,请核对数据！");
            }
        }
        List<Entry> list = new ArrayList<Entry>();
        List<String> personList = new ArrayList<String>();
        List<Entry> jxEntryList = this.getJxEntryList(entryNo);
        for (Entry entry : jxEntryList) {
            personName2Entry.put(entry.getEntryKhpersonname(), entry);
        }
        int i = 0;
        int sucCount = 0;
        String personMsg = "";
        try {

            for (Map<String, Object> map : dataList) {
                i++;
                if (i == 1) continue;//列名
                //System.out.println("-----------------"+map.get(tmap.get(titles[1])));
                Object personDate = map.get(tmap.get(titles[1]));
                Object indexData = map.get(tmap.get(titles[0]));
                Object ratingDate = map.get(tmap.get(titles[2]));
                if ((personDate == null || personDate.toString().trim().equals("")) && (indexData == null || indexData.toString().trim().equals(""))) {
                    i--;
                    break;//识为excel编辑动到空格了。。
                }
                String person = map.get(tmap.get(titles[1])).toString().trim();
                if (personList.contains(person)) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">录入有误！在前面行已经有此人数据！");
                }
                personList.add(person);
                String[] parr = person.split("_");
                if (parr.length != 2) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">设置有误！请按（姓名_工号）填写！");
                }
                if (!personName2Entry.containsKey(person)) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">不存在考核中！");
                }
                if (ratingDate != null) {
                    Entry entry = personName2Entry.get(person);
                    String type = entry.getEntryApptype();
                    if ("4".equals(type)) {
                        String sql = "update ct_jx_entry set entry_rating=?  where entry_id = ?";
                        Db.update(sql, ratingDate.toString().trim(), entry.getEntryId());
                        sucCount++;
                    } else {
                        personMsg = personMsg + entry.getEntryKhpersonname() + ",";
                    }

                }


            }
        } catch (Exception e) {
            log.error("excel导入考核失败", e);
            return exceptionReturn("Excel读取到" + (i - 1) + "行时出现错误！" + e.getMessage());
        }

        DataBean dBean = new DataBean();
        dBean.setMsg("成功导入" + sucCount + "条评级！" + (personMsg.length() > 0 ? "以下人员数据不是评分确认状态本次不更新评级数据:" + personMsg : ""));
        dBean.setCode(1);
        return dBean;
    }

    @Before(Tx.class)
    public DataBean importJxKpiData(List<Map<String, Object>> dataList, String entryNo, Person operator, String khcycle, String khorg, boolean isJxjl, boolean isAdmin) {
        String pid = operator.getId();

        if (dataList == null || dataList.size() < 2) {
            return exceptionReturn("缺少数据！");
        }
        Org org = null;
        Cycle cycle = null;
        String orgName = null;
        List<String> oldPersonIdList = new ArrayList<>();
        if (StringUtils.isNotBlank(entryNo)) {
            EntryNo entryno = EntryNo.dao.findById(entryNo);
            khorg = entryno.getEntrynoOrgid();
            khcycle = entryno.getEntrynoCycleid();

            org = Org.dao.findById(entryno.getEntrynoOrgid());
            orgName = entryno.getEntrynoOrgname();
            String entryNoStatus = entryno.getEntrynoAppnode();
            if (entryNoStatus.equals("5") || entryNoStatus.equals("7")) {

            } else if (!entryNoStatus.equals("0")) {
                return exceptionReturn("当前状态不允许导入被考核人员数据！");
            }
            List<Entry> jxEntryList = this.getJxEntryList(entryNo);
            for (Entry entry : jxEntryList) {
                oldPersonIdList.add(entry.getEntryKhpersonid());
            }
        } else {
            if (StringUtils.isBlank(khcycle)) {
                return exceptionReturn("请选择考核周期！");
            }
            if (StringUtils.isBlank(khorg)) {
                return exceptionReturn("请选择考核组织！");
            }


            List<Org> enableOrgList = orgService.getEnableOrgList(pid);

            for (Org o : enableOrgList) {
                if (o.getOrgId().equals(khorg)) {
                    org = o;
                    orgName = o.getOrgName();
                    break;
                }
            }
        }

        cycle = Cycle.dao.findById(khcycle);


        if (cycle == null) {
            return exceptionReturn("考核周期数据异常，请重试！");
        }

        if (org == null) {
            return exceptionReturn("考核组织数据异常，请重试！");
        }

        // String[] titles = {"序号", "被考核人", "上级"};
        String[] titles = {"序号", "被考核人姓名", "被考核人工号"};
        Map<String, Object> titleMap = dataList.get(0);
        Map<String, String> tmap = new HashMap<String, String>();//表头-FX 映射
        for (String s : titleMap.keySet()) {
            tmap.put(titleMap.get(s).toString().trim(), s);
        }
        for (String title : titles) {

            if (!tmap.containsKey(title)) {
                return exceptionReturn("缺少列<" + title + ">,请核对数据！");
            }
        }
        List<Person> list = new ArrayList<Person>();
        List<String> personList = new ArrayList<String>();
        Map<String, Person> superMap = new HashMap<>();
        int i = 0;
        try {

            for (Map<String, Object> map : dataList) {
                i++;
                if (i == 1) continue;//列名
                //System.out.println("-----------------"+map.get(tmap.get(titles[1])));
                Object personName = map.get(tmap.get(titles[1]));
                Object personNo = map.get(tmap.get(titles[2]));
                Object indexData = map.get(tmap.get(titles[0]));
                if ((personName == null || personName.toString().trim().equals("")) && (indexData == null || indexData.toString().trim().equals(""))) {
                    i--;
                    break;//识为excel编辑动到空格了。。
                }
                if (StringUtils.isBlank(personName.toString()) || StringUtils.isBlank(personNo.toString())) {
                    return exceptionReturn("Excel第" + i + "行被考核人姓名或工号为空！");
                }
                String person = personName.toString().trim() + "_" + personNo.toString().trim();
                if (personList.contains(person)) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">录入有误！在前面行已经有此人数据！");
                }
                personList.add(person);
//                String[] parr = person.split("_");
//                if (parr.length != 2) {
//                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">设置有误！请按（姓名_工号）填写！");
//                }
                Person p = hrService.getPersonByNumberAndName(personNo.toString(), personName.toString());
                if (p == null) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">设置有误！未查到此人！(确认是否离职或职位为空！)");
                }
                if (oldPersonIdList.contains(p.getId())) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">已存在！请勿重复导入！");
                }
//                if(StringUtils.isNotBlank(superPerson)){
//                    Person sp = superMap.get(superPerson);
//                    if(sp == null){
//                        String[] pparr = superPerson.split("_");
//                        if (pparr.length != 2) {
//                            return exceptionReturn("Excel第" + i + "行上级<" + superPerson + ">设置有误！请按（姓名_工号）填写！");
//                        }
//                        sp = hrService.getPersonByNumberAndName(pparr[1], pparr[0]);
//                        if (sp == null) {
//                            return exceptionReturn("Excel第" + i + "行被考核人<" + superPerson + ">设置有误！未查到此人！(确认是否离职或职位为空！)");
//                        }
//                        superMap.put(superPerson,sp);
//                    }
//                    p.put("super", sp);
//                }

                String entryId = Tool.uuid();
                p.put("entryId", entryId);
                list.add(p);


            }
        } catch (Exception e) {
            log.error("excel导入考核失败", e);
            return exceptionReturn("Excel读取到" + (i - 1) + "行时出现错误！" + e.getMessage());
        }
        try {
            this.saveEntrys(list, org.getOrgId(), orgName, cycle, entryNo, operator);
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException("导入失败!" + e.getMessage());
            //return exceptionReturn(e.getMessage());
        }

        DataBean dBean = new DataBean();
        dBean.setMsg("成功录入" + (list.size()) + "条数据！");
        dBean.setCode(1);
        return dBean;
    }

    @Before(Tx.class)
    public DataBean importOfflineData(List<Map<String, Object>> dataList, String entryNo, Person operator, String khcycle, String khorg, String startDate, boolean isJxjl, boolean isAdmin) {
        String pid = operator.getId();
        if (dataList == null || dataList.size() < 2) {
            return exceptionReturn("缺少数据！");
        }
        Org org = null;
        Cycle cycle = null;
        String orgName = null;
        if (StringUtils.isNotBlank(entryNo)) {
            EntryNo entryno = EntryNo.dao.findById(entryNo);
            khorg = entryno.getEntrynoOrgid();
            khcycle = entryno.getEntrynoCycleid();
            org = Org.dao.findById(entryno.getEntrynoOrgid());
            orgName = entryno.getEntrynoOrgname();
            startDate = this.getJxEntryList(entryNo).get(0).getEntrySubmittime();
        } else {
            if (StringUtils.isBlank(khcycle)) {
                return exceptionReturn("请选择考核周期！");
            }
            if (StringUtils.isBlank(khorg)) {
                return exceptionReturn("请选择考核组织！");
            }
            if (StringUtils.isBlank(startDate)) {

                return exceptionReturn("请选择发起日期！");
            } else {
                if (Tool.getCurrDate().compareTo(startDate) < 0) {
                    return exceptionReturn("发起日期不能晚于当前时间！");
                }
            }
            startDate = startDate + " 00:00:00";

            List<Org> enableOrgList = orgService.getEnableOrgList(pid);
            for (Org o : enableOrgList) {
                if (o.getOrgId().equals(khorg)) {
                    org = o;
                    orgName = o.getOrgName();
                    break;
                }
            }
        }
        cycle = Cycle.dao.findById(khcycle);
        if (cycle == null) {
            return exceptionReturn("考核周期数据异常，请重试！");
        }
        if (org == null) {
            return exceptionReturn("考核组织数据异常，请重试！");
        }
        // String[] titles = {"序号","被考核人","自评总分", "上级领导", "汇总得分", "评级"};
        String[] titles = {"序号", "被考核人姓名", "被考核人工号", "自评总分", "上级领导姓名", "上级领导工号", "汇总得分", "评级"};
        Map<String, Object> titleMap = dataList.get(0);
        Map<String, String> tmap = new HashMap<String, String>();//表头-FX 映射
        for (String s : titleMap.keySet()) {
            tmap.put(titleMap.get(s).toString().trim(), s);
        }
        for (String title : titles) {
            if (title.equals("序号") || title.equals("部门")) {
                continue;
            }

            if (!tmap.containsKey(title)) {
                return exceptionReturn("缺少列<" + title + ">,请核对数据！");
            }
        }
        List<Person> list = new ArrayList<Person>();
        String entryId = null;
        int i = 0;
        List<String> personList = new ArrayList<String>();
        try {
            for (Map<String, Object> map : dataList) {

                i++;
                if (i == 1) continue;//列名
                //被考考核人
                Object personData = map.get(tmap.get(titles[1]));
                if ((personData == null || StringUtils.isBlank(personData.toString()))) {
                    i--;
                    break;//识为excel编辑动到空格了。。
                }
                //被考核人
                String person = map.get(tmap.get(titles[1])).toString().trim() + "_" + map.get(tmap.get(titles[2])).toString().trim();
                String superPerson = map.get(tmap.get(titles[4])).toString().trim() + "_" + map.get(tmap.get(titles[5])).toString().trim();
                //被考核部门
                // String dept = map.get(tmap.get(titles[2])).toString().trim();
                BigDecimal score = null;
                String rating = map.get(tmap.get(titles[7])).toString().trim();
                try {
                    score = new BigDecimal(map.get(tmap.get(titles[6])).toString().trim());
                } catch (Exception e) {
                    return exceptionReturn("Excel第" + i + "行考核得分录入有误！");
                }
                BigDecimal zpScore = null;
                try {
                    zpScore = new BigDecimal(map.get(tmap.get(titles[3])).toString().trim());
                } catch (Exception e) {
                    return exceptionReturn("Excel第" + i + "行" + titles[3] + "录入有误！");
                }

                if (personList.contains(person)) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">录入有误！在前面行已经有此人KPI数据！");
                }

                Person p = hrService.getPersonByNumberAndName(map.get(tmap.get(titles[2])).toString().trim(), map.get(tmap.get(titles[1])).toString().trim());
                if (p == null) {
                    return exceptionReturn("Excel第" + i + "行被考核人<" + person + ">设置有误！未查到此人！(确认是否离职或职位为空！)");
                }

//
                Person sp = hrService.getPersonByNumberAndName(map.get(tmap.get(titles[5])).toString().trim(), map.get(tmap.get(titles[4])).toString().trim());
                if (sp == null) {
                    return exceptionReturn("Excel第" + i + "行上级领导<" + superPerson + ">设置有误！未查到此人！(确认是否离职或职位为空！)");
                }


                if (!("A".equals(rating) || "B".equals(rating) || "C".equals(rating) || "D".equals(rating) || "S".equals(rating))) {
                    return exceptionReturn("Excel第" + i + "行评级录入有误！,必须为A/B/C/D/S!");
                }

                entryId = Tool.uuid();
                p.put("entryId", entryId);
                p.put("score", score);
                p.put("zpScore", zpScore);
                p.put("rating", rating);
                p.put("super", sp);
                list.add(p);
                if (!personList.contains(person)) {
                    personList.add(person);
                }
            }
        } catch (Exception e) {
            log.error("excel导入考核失败", e);
            return exceptionReturn("Excel读取到" + (i - 1) + "行时出现错误！！" + e.getMessage());
        }

        try {
            this.saveOfflineEntrys(list, org.getOrgId(), orgName, cycle, entryNo, startDate, operator);
        } catch (Exception e) {
            String m = e.getMessage();
            if (m == null || m.indexOf("Exception") > 0) {
                e.printStackTrace();
            }
            throw new RuntimeException("导入失败!" + e.getMessage());
            //return exceptionReturn(e.getMessage());
        }
        DataBean dBean = new DataBean();
        dBean.setMsg("成功录入" + (i - 1) + "条数据！");
        dBean.setCode(1);
        return dBean;
    }


    private Kpi copyExp(Kpi k) {
        Kpi kpi = new Kpi();
        kpi.setKpiIndex(k.getKpiIndex());
        kpi.setKpiEntryid(k.getKpiEntryid());
        kpi.setKpiName(k.getKpiName());
        kpi.setKpiTarget(k.getKpiTarget());
        kpi.setKpiType(k.getKpiType());
        kpi.setKpiDefine(k.getKpiDefine());
        kpi.setKpiCaption(k.getKpiCaption());
        kpi.setKpiWeight(k.getKpiWeight());
        kpi.setKpiNum(k.getKpiNum());
        kpi.put("expList", k.get("expList"));
        return kpi;
    }

    /**
     * key - kpilibName
     *
     * @return
     */
    private Map<String, Kpilib> getEnableKpilib(String orgId) {
        Map<String, Kpilib> map = new HashMap<>();
        List<Kpilib> kpilibList = kpilibService.getKpilibList(orgId);
        for (Kpilib kpilib : kpilibList) {
            map.put(kpilib.getKpilibName(), kpilib);
        }
        return map;
    }

    /**
     * key - kpilibName
     *
     * @return
     */
    private Map<String, Kpilib> getAllKpilibName() {
        Map<String, Kpilib> map = new HashMap<>();
        List<Kpilib> kpilibList = kpilibService.getKpilib(new Kpilib());
        for (Kpilib kpilib : kpilibList) {
            map.put(kpilib.getKpilibName(), kpilib);
        }
        return map;
    }

    public List<Kpi> getKpiByWhere(Kpi kpi) {
        Conditions condi = new Conditions();
        condi.modelToCondition(kpi);
        SqlPara sp = condi.getSqlPara();
//        sp.setSql(sp.getSql() + "  order by len(kpi_num),kpi_num asc  ");
        sp.setSql(sp.getSql() + "  order by length(kpi_num),kpi_num asc  ");//oracle 调整
        return Kpi.dao.find(sp);
    }

    public List<Entry> getJxEntryByWhere(Entry entry) {
        Conditions condi = new Conditions();
        condi.modelToCondition(entry);
        SqlPara sp = condi.getSqlPara();
        sp.setSql(sp.getSql() + "  order by entry_apptime asc");
        return Entry.dao.find(sp);
    }


    /**
     * 根据entryno 获取考核人员信息
     *
     * @return
     */
    public List<Entry> getJxEntryList(String entryno) {
        String sql = "select * from ct_jx_entry where entry_no = ? order by entry_displayname asc";
        List<Entry> jxEntries = Entry.dao.find(sql, entryno);
        return jxEntries;
    }

    /**
     * 根据entryno 获取考核人员信息
     *
     * @return
     */
    public List<Entry> getJxEntryListByType(String entryno, String type) {
        String sql = "select * from ct_jx_entry where entry_no = ? and entry_apptype = ? order by entry_displayname asc";
        List<Entry> jxEntries = Entry.dao.find(sql, entryno, type);
        return jxEntries;
    }

    /**
     * 根据entryno 获取考核人员信息
     *
     * @return
     */
    public List<Entry> getJxEntryList(String entryno, String personName) {
        String sql = "select * from ct_jx_entry where entry_no = ? order by entry_displayname asc";
        List<Entry> jxEntries = null;
        if (StringUtils.isNotBlank(personName)) {
            sql = "select * from ct_jx_entry where entry_no = ? and entry_khpersonname like ? order by entry_displayname asc";
            jxEntries = Entry.dao.find(sql, entryno, "%" + personName + "%");
        } else {
            jxEntries = Entry.dao.find(sql, entryno);
        }

        return jxEntries;
    }

    /* 根据entryno 获取考核人员信息  增加获取 1，2，3级领导
     *
     * @return
     */
    public List<Entry> getJxEntryListAndManager(String entryno, String personName) {
        //
        String sql = "select e.* ,d.personmanager_pname1 super1,d.personmanager_pname2 super2,d.personmanager_pname3 super3,p2.fname_l2  hrsuper  " +
                ",(select count(*) from ct_jx_attachment where attachment_entryid =entry_id) attachmentCnt  from ct_jx_entry e " +
                "  left join ct_jx_personmanager d on e.entry_khpersonid = d.personmanager_id  " +
                " left join t_bd_person p1 on p1.fid = e.entry_khpersonid " +
                " left join t_bd_person p2 on p1.cfleaderid = p2.fid" +
                " where entry_no = ? order by entry_displayname asc";
        List<Entry> jxEntries = null;
        if (StringUtils.isNotBlank(personName)) {
            sql = "select e.* ,d.personmanager_pname1 super1,d.personmanager_pname2 super2,d.personmanager_pname3 super3,p2.fname_l2  hrsuper  " +
                    ",(select count(*) from ct_jx_attachment where attachment_entryid =entry_id) attachmentCnt  from ct_jx_entry e " +
                    "  left join ct_jx_personmanager d on e.entry_khpersonid = d.personmanager_id  " +
                    " left join t_bd_person p1 on p1.fid = e.entry_khpersonid " +
                    " left join t_bd_person p2 on p1.cfleaderid = p2.fid" +
                    " where entry_no = ?  and entry_khpersonname like ? order by entry_displayname asc";
            jxEntries = Entry.dao.find(sql, entryno, "%" + personName + "%");
        } else {
            jxEntries = Entry.dao.find(sql, entryno);
        }

        return jxEntries;
    }

    /**
     * 是否所有entry 都是某个节点状态
     *
     * @param entryno
     * @param appType
     * @return
     */
    public boolean isAllEntryStatus(String entryno, String appType) {
        String sql = "select count(1)count,sum(case when entry_apptype=? then 1 else 0 end) appcount from ct_jx_entry where entry_no = ? ";
        List<Entry> list = Entry.dao.find(sql, appType, entryno);
        if (list.size() == 0) {
            return false;
        }
        Entry entry = list.get(0);
        return entry.getInt("count") > 0 && entry.getInt("count") == entry.getInt("appcount");
    }

    /**
     * 是否所有entry 都是某两个节点状态
     *
     * @param entryno
     * @param appType
     * @return
     */
    public boolean isAllEntryStatus(String entryno, String appType, String appType1) {
        String sql = "select count(1)count,sum(case when entry_apptype=? or entry_apptype=? then 1 else 0 end) appcount from ct_jx_entry where entry_no = ? ";
        List<Entry> list = Entry.dao.find(sql, appType, appType1, entryno);
        if (list.size() == 0) {
            return false;
        }
        Entry entry = list.get(0);
        return entry.getInt("count") > 0 && entry.getInt("count") == entry.getInt("appcount");
    }

    /**
     * 根据kpiid删除KPI及对应的公式
     */
    @Before(Tx.class)
    public void delJxKpi(String kpiid, Person person) {
        /**
         * 如果要删除的数据为 同一指标中多个考核人的数据 且为同一指标第一位的数据
         *  需要在删除前，给非第一位的数据设置为  第一位
         */
        Kpi k = Kpi.dao.findById(kpiid);
        Entry entry = Entry.dao.findById(k.getKpiEntryid());
        String appNode = entry.getEntryApptype();
        if (StringUtils.isNotBlank(appNode) && !"0".equals(appNode) && !"5".equals(appNode) && !"6".equals(appNode) && !"7".equals(appNode)) {
            throw new RuntimeException("当前流程状态无法删除指标明细！");
        }
        if (StringUtils.isNotBlank(appNode) && !"0".equals(appNode) && !"5".equals(appNode)) {
            wflogService.addWfLog(person, "绩效专员(" + person.getName() + ")删除指标,流程节点类型:" + entry.getEntryApptype(), "9", entry.getEntryCycleid(), entry.getEntryId(), entry.getEntryNo(), "", k.getKpiName());
        }
        Kpi.dao.deleteById(kpiid);
//        //删除公式
//        String sql = "delete from ct_jx_exp where exp_kpiid = '" + kpiid + "' ";
//        Db.delete(sql);

        // resetKpiHead(k.getKpiEntryid());

    }

    /**
     * 根据entryid删除考核人员信息
     *
     * @param entryid
     */
    @Before(Tx.class)
    public void delJxEntry(String entryid, Person person) {

        Entry entry = Entry.dao.findById(entryid);
        EntryNo entryNo = this.getEntryNoByEntryId(entryid);
        String entryApptype = entry.getEntryApptype();

        if ("0".equals(entryApptype) || "5".equals(entryApptype) || "6".equals(entryApptype) || "7".equals(entryApptype) || "2".equals(entryNo.getEntrynoOnline())) {

        } else if (!("9".equals(entryApptype) && "1".equals(entry.getEntryOffline()))) {
            throw new RuntimeException("评分开始后不允许删除！");

        }

        String s = "delete from ct_jx_kpi where kpi_entryid = '" + entryid + "' ";
        Db.delete(s);
        entry.delete();
        if (!"1".equals(entry.getEntryOffline())) {
            if (!"0".equals(entryApptype)) {
                wflogService.addWfLog(person, "绩效专员(" + person.getName() + ")删除被考核人:" + entry.getEntryKhpersonname() + ",流程节点类型:" + entryApptype, "9", entry.getEntryCycleid(), entry.getEntryId(), entry.getEntryNo(), "", "");
            }
            if (this.isAllEntryStatus(entry.getEntryNo(), "7")) {
                EntryNo eno = EntryNo.dao.findById(entry.getEntryNo());
                eno.setEntrynoAppnode("7");
                eno.update();
            }
        }

    }


    /**
     * 根据entryid获取考核人员的KPI
     *
     * @param entryid
     */
    public List<Kpi> getKpiList(String entryid) {
        //String sql = "select k.*,e.*,(select count(*) from ct_jx_attachment where attachment_kpiid = k.kpi_id ) attachmentCnt from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id  where kpi_entryid = ?    order by kpi_type,len(kpi_num),kpi_num  asc ";
        // String sql = "select k.*,e.*,(select count(*) from ct_jx_attachment where attachment_kpiid = k.kpi_id ) attachmentCnt from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id  where kpi_entryid = ?    order by kpi_type,length(kpi_num),kpi_num  asc ";//oracle 调整
        String sql = "select k.*,e.*,0 attachmentCnt from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id  where kpi_entryid = ?    order by kpi_type,length(kpi_num),kpi_num  asc ";//oracle 调整

        return Kpi.dao.find(sql, entryid);
    }

    /**
     * 根据entryid获取考核人员的KPI
     *
     * @param entryid
     */
    public List<Kpi> getKpiSimpleList(String entryid) {
        //String sql = "select * from ct_jx_kpi where kpi_entryid=? order by kpi_type,len(kpi_num),kpi_num  asc ";
        String sql = "select * from ct_jx_kpi where kpi_entryid=? order by kpi_type,length(kpi_num),kpi_num  asc ";//oracle 调整
        return Kpi.dao.find(sql, entryid);
    }

    /**
     * 获取一次提交中的 所有KPI
     *
     * @param entryNo
     */
    public List<Kpi> getKpiListByNo(String entryNo) {
        //String sql = "select * from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id where e.entry_no = ? order by entry_displayname, kpi_entryid,kpi_type, len(kpi_num),kpi_num  asc";
        String sql = "select * from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id where e.entry_no = ? order by entry_displayname, kpi_entryid,kpi_type, length(kpi_num),kpi_num  asc";//oracle 调整

        return Kpi.dao.find(sql, entryNo);
    }

    /**
     * 获取一次提交中的 所有KPI
     *
     * @param kpiId
     */
    public Kpi getKpiInfo(String kpiId) {
        String sql = "select * from ct_jx_kpi k left join ct_jx_entry e on k.kpi_entryid=e.entry_id where k.kpi_id = ? ";
        List<Kpi> list = Kpi.dao.find(sql, kpiId);
        return list != null ? list.get(0) : null;

    }

    /**
     * 同周期下 是否有了某员工的考核
     *
     * @param personId
     * @param cycleId
     * @param entryNo  排除本次NO  新增的传null
     * @return
     */
    public Entry isExist(String personId, String cycleId, String entryNo) {
        Entry entry = new Entry();
        entry.setEntryKhpersonid(personId);
        entry.setEntryCycleid(cycleId);
        // entry.setEntryNo(entryNo);
        Conditions condi = new Conditions();
        condi.modelToCondition(entry);
        SqlPara sp = condi.getSqlPara();
        List<Entry> list = Entry.dao.find(sp);
        if (list == null || list.size() == 0) {
            return null;
        }
        if (StringUtils.isBlank(entryNo)) return list.get(0);
        for (Entry e : list) {
            if (!entryNo.equals(e.getEntryNo())) {
                return e;
            }
        }
        return null;
    }

    /**
     * 计算考核人员最终得分(只有当该考核人员的所有评分人评分完毕，才能计算出最终得分
     * 否则返回)
     *
     * @param entryid
     */
    public void updateJxEntryScore(String entryid) {
        boolean flag = false;
        Kpi kpiWhere = new Kpi();
        kpiWhere.setKpiEntryid(entryid);
        //计算最后得分
        BigDecimal score = new BigDecimal("0");
        List<Kpi> kpiByWhere = getKpiByWhere(kpiWhere);
        for (Kpi k : kpiByWhere) {
            if (k.getKpiRealscore() != null) {
                score = score.add(k.getKpiRealscore());
            } else if ("3".equals(k.getKpiType())) {
                score = k.getKpiScore() != null ? score.add(k.getKpiScore()) : score;
            } else {
                flag = true;
                break;
            }
        }
        Entry entry = Entry.dao.findById(entryid);
        if (!flag) {
            entry.setEntryScore(score);
        } else {
            entry.setEntryScore(null);
        }
        entry.update();
    }

    public void updateJxEntryScoreAndRating(Entry entry, String rating) {
        boolean flag = false;
        Kpi kpiWhere = new Kpi();
        kpiWhere.setKpiEntryid(entry.getEntryId());
        //计算最后得分
        BigDecimal score = new BigDecimal("0");
        List<Kpi> kpiByWhere = getKpiByWhere(kpiWhere);
        for (Kpi k : kpiByWhere) {
            if (k.getKpiRealscore() != null) {
                score = score.add(k.getKpiRealscore());
            } else if ("3".equals(k.getKpiType())) {
                score = k.getKpiScore() != null ? score.add(k.getKpiScore()) : score;
            } else {
                flag = true;
                break;
            }
        }
        if (!flag) {
            entry.setEntryScore(score);
        } else {
            entry.setEntryScore(null);
        }
        entry.setEntryRating(rating);
        entry.update();
    }


    public void updateJxEntryZpScore(String entryid) {
        boolean flag = false;
        Kpi kpiWhere = new Kpi();
        kpiWhere.setKpiEntryid(entryid);
        //计算最后得分
        BigDecimal score = new BigDecimal("0");
        List<Kpi> kpiByWhere = getKpiByWhere(kpiWhere);
        for (Kpi k : kpiByWhere) {
            if ("3".equals(k.getKpiType())) {
                continue;
            }
            if (k.getKpiZpscore() == null || k.getKpiWeight() == null) {
                flag = true;
                break;
            }
            score = score.add(k.getKpiZpscore().multiply(k.getKpiWeight()).divide(new BigDecimal("100")));

        }
        Entry entry = Entry.dao.findById(entryid);
        if (!flag) {
            entry.setEntryZpscore(score.setScale(2, RoundingMode.HALF_UP));
        } else {
            entry.setEntryZpscore(null);
        }
        entry.update();
    }

    /**
     * 新增保存所有考核信息
     *
     * @param list    被考核人  person放入key:entryId  分录Id
     * @param orgId
     * @param orgName
     * @param cycle
     * @param entryno 覆盖导入请传值，不覆盖不传
     * @param creator
     */
    @Before(Tx.class)
    public List<Entry> saveEntrys(List<Person> list, String orgId, String orgName, Cycle cycle, String entryno, Person creator) {
        boolean beforScoreWf = false;
        boolean entryNoApp7 = false;
        EntryNo entryNo = null;
        if (StringUtils.isNotBlank(entryno)) {//不为空的  判断是否已经有了考核entry，重复被考核人的  直接删掉覆盖对应entry（适合增量覆盖逻辑）

            List<Entry> existList = this.getJxEntryList(entryno);
            //
            if (existList != null && existList.size() > 0) {
                List<String> pidList = new ArrayList<String>();
                for (Person khperson : list) {
                    pidList.add(khperson.getId());
                }
                for (Entry entry : existList) {
                    if (pidList.contains(entry.getEntryKhpersonid())) {
                        delJxEntry(entry.getEntryId(), creator);
                    }
                }
            }
            entryNo = this.getEntryNoById(entryno);
            String entryNoStatus = entryNo.getEntrynoAppnode();
            if (entryNoStatus.equals("5") || entryNoStatus.equals("7")) {
                beforScoreWf = true;
            }
            if (entryNoStatus.equals("7")) {
                entryNoApp7 = true;
            }

        } else {
            entryNo = this.addEntryNo(cycle.getCycleId(), orgId, creator);
            entryno = entryNo.getEntrynoId();

        }

        List<Entry> elist = new ArrayList<Entry>();
        boolean entryApp5 = false;
        String currTime = Tool.getCurrTime();
        List<Entry> addKpiEntryList = new ArrayList<>();
        Map<String, Person> personManagerMap = new HashMap<>();
        Map<String, Person> allEnablePerson = hrService.getAllEnablePerson().stream().collect(Collectors.toMap(Person::getId, p -> p));
        for (Person khperson : list) {
            Entry e = isExist(khperson.getId(), cycle.getCycleId(), null);
            if (e != null) {
                throw new RuntimeException("周期<" + cycle.getCycleName() + ">下已存在员工:" + khperson.getName() + "的考核！考核组织为：" + e.getEntryOrgname());
            }
            Entry jxEntry = new Entry();
            jxEntry.setEntryId(khperson.get("entryId").toString());
            jxEntry.setEntryCycleid(cycle.getCycleId());
            jxEntry.setEntryCyclename(cycle.getCycleName());
            jxEntry.setEntryKhpersonid(khperson.getId());
            jxEntry.setEntryKhpersonname(khperson.getName());
            jxEntry.setEntryKhdeptid(khperson.getDeptId());
            jxEntry.setEntryKhdeptname(khperson.getDeptName());
            jxEntry.setEntryDisplayname(khperson.getCname());
            jxEntry.setEntryKhpositionname(khperson.getPositionName());
            jxEntry.setEntryKhpositionid(khperson.getPositionId());
            jxEntry.setEntryOrgid(orgId);
            jxEntry.setEntryOrgname(orgName);
            jxEntry.setEntryApptype("0");//编辑状态
            jxEntry.setEntryWfstatus("0");//未触发
            jxEntry.setEntryNo(entryno);
            jxEntry.setEntryCreatetime(currTime);
            jxEntry.setEntryCreatorid(creator.getId());
            jxEntry.setEntryCreatorname(creator.getName());
            BigDecimal self = new BigDecimal(100);
            jxEntry.setEntrySelfkpiweight(self == null ? new BigDecimal(0) : self);
            if (beforScoreWf) {
                jxEntry.setEntryWfstatus("1");
                if (self == null || self.compareTo(new BigDecimal(0)) == 0) {
                    jxEntry.setEntryApptype("7");
                } else {
                    jxEntry.setEntryApptype("5");
                    entryApp5 = true;

                }
                jxEntry.setEntryApptime(currTime);
                addKpiEntryList.add(jxEntry);
                wflogService.addWfLog(creator, "绩效专员(" + creator.getName() + ")追加导入被考核人" + jxEntry.getEntryKhpersonname(), "9", jxEntry.getEntryCycleid(), jxEntry.getEntryId(), jxEntry.getEntryNo(), "1", "");
            }
            if ("5".equals(jxEntry.getEntryApptype())) {
                //获取考核人上级
                String personId = khperson.getId();
                Person superPerson = null;
                if (!personManagerMap.containsKey(personId)) {
                    try {
                        superPerson = personManagerService.getManager(personId, 1, allEnablePerson);
                    } catch (Exception ex) {
                    }
                    if (superPerson == null) {
                        throw new RuntimeException("获取员工:" + khperson.getName() + "的上级失败！");
                    }
                    personManagerMap.put(personId, superPerson);
                } else {
                    superPerson = personManagerMap.get(personId);
                }
                //更新 ct_jx_entry 中流程节点为  领导审批kpi
                jxEntry.setEntrySuperId(superPerson.getId());
                jxEntry.setEntrySuperName(superPerson.getName());
            }

            jxEntry.save();
            if ("5".equals(jxEntry.getEntryApptype())) {
                try {
                    //mailService.sendJxEmail(jxEntry.getEntryId(),"1","10");
                    wxMsgService.sendEntryWxMsg(jxEntry, WxMsgType.GRMB, khperson);
                } catch (Exception e1) {
                    log.error("提醒员工编辑绩效指标微信发送失败：" + e1.getMessage() + ",员工：" + jxEntry.getEntryKhpersonname());
                }
            }

            elist.add(jxEntry);
        }
        if (entryApp5 && entryNoApp7) {
            entryNo.setEntrynoAppnode("5");
            entryNo.update();
        }
//        initKpi(addKpiEntryList);
        return elist;

    }

    /**
     * 根据模板生成指标数据
     *
     * @param entryList
     */
    @Before(Tx.class)
    public void initKpi(List<Entry> entryList) {
        List<Kpitemplate> kpitemplates = Kpitemplate.dao.find("select * from ct_jx_kpitemplate order by kpitemplate_type,kpitemplate_num");
//        List<String> templateType = new ArrayList<>();
        List<String> typeList = kpitemplates.stream().map(Kpitemplate::getKpitemplateType).collect(Collectors.toList());
        for (Entry entry : entryList) {
            String entryId = entry.getEntryId();
            List<Kpi> kpiList = this.getKpiSimpleList(entryId);
            boolean flag = false; //是否存在模板数据
            if (kpiList != null && kpiList.size() > 0) {
                for (Kpi kpi : kpiList) {
                    if (typeList.contains(kpi.getKpiType())) {
                        flag = true;
                        break;
                    }
                }
            }
            if (!flag) {
                int index = 1;
                String prevType = "";
                for (Kpitemplate temp : kpitemplates) {
                    String type = temp.getKpitemplateType();
                    if (type.equals(prevType)) {
                        index++;
                    } else {
                        index = 1;
                        prevType = type;
                    }
                    Kpi kpi = new Kpi();
                    String kid = Tool.uuid();
                    kpi.setKpiId(kid);
                    kpi.setKpiEntryid(entryId);
                    kpi.setKpiName(temp.getKpitemplateName());
                    kpi.setKpiType(type);
                    kpi.setKpiDefine(temp.getKpitemplateDefine());
                    kpi.setKpiCaption(temp.getKpitemplateCaption());
                    kpi.setKpiTarget(temp.getKpitemplateTarget());
                    kpi.setKpiWeight(temp.getKpitemplateWeight());
                    kpi.setKpiNum(temp.getKpitemplateNum());
                    kpi.setKpiIsSelf("2");
                    kpi.setKpiIndex(index);
                    kpi.save();
                }
            }
        }

    }


    /**
     * 新增保存所有考核信息
     *
     * @param list    被考核人  person放入key:entryId  分录Id
     * @param orgId
     * @param orgName
     * @param cycle
     * @param entryno 覆盖导入请传值，不覆盖不传
     * @param creator
     */
    @Before(Tx.class)
    public void saveOfflineEntrys(List<Person> list, String orgId, String orgName, Cycle cycle, String entryno, String startDate, Person creator) {
        if (StringUtils.isNotBlank(entryno)) {

        } else {
            EntryNo entryNo = this.addEntryNo(cycle.getCycleId(), orgId, creator);
            entryNo.setEntrynoOnline("2");
            entryNo.setEntrynoAppnode("9");
            entryNo.update();
            entryno = entryNo.getEntrynoId();
        }

        for (Person khperson : list) {
            Entry e = isExist(khperson.getId(), cycle.getCycleId(), null);
            if (e != null) {
                throw new RuntimeException("周期<" + cycle.getCycleName() + ">下已存在员工:" + khperson.getName() + "的考核！考核组织为：" + e.getEntryOrgname());
            }
            //获取考核人上级
            Person superPerson = khperson.get("super");
            Entry jxEntry = new Entry();
            jxEntry.setEntryId(khperson.get("entryId").toString());
            jxEntry.setEntryCycleid(cycle.getCycleId());
            jxEntry.setEntryCyclename(cycle.getCycleName());
            jxEntry.setEntryKhpersonid(khperson.getId());
            jxEntry.setEntryKhpersonname(khperson.getName());
            jxEntry.setEntryKhdeptid(khperson.getDeptId());
            jxEntry.setEntryKhdeptname(khperson.getDeptName());
            jxEntry.setEntryDisplayname(khperson.getCname());
            jxEntry.setEntryKhpositionname(khperson.getPositionName());
            jxEntry.setEntryKhpositionid(khperson.getPositionId());
            jxEntry.setEntryOrgid(orgId);
            jxEntry.setEntryOrgname(orgName);
            jxEntry.setEntryScore(new BigDecimal(khperson.get("score").toString()));
            jxEntry.setEntryZpscore(new BigDecimal(khperson.get("zpScore").toString()));
            jxEntry.setEntryApptype("9");//结束
            jxEntry.setEntryWfstatus("9");//结束
            jxEntry.setEntryRating(khperson.get("rating").toString());
            jxEntry.setEntryNo(entryno);
            jxEntry.setEntryCreatetime(startDate);
            jxEntry.setEntrySubmittime(startDate);
            jxEntry.setEntryCreatorid(creator.getId());
            jxEntry.setEntryCreatorname(creator.getName());
            jxEntry.setEntrySuperId(superPerson.getId());
            jxEntry.setEntrySuperName(superPerson.getName());
            jxEntry.setEntryOffline("1");
            jxEntry.save();

            wflogService.addWfLog(creator, "绩效专员(" + creator.getName() + ")导入线下考核数据", "9", jxEntry.getEntryCycleid(), jxEntry.getEntryId(), jxEntry.getEntryNo(), "1", "");

        }

    }


    public EntryNo addEntryNo(String cycleId, String orgid, Person person) {
        EntryNo oldEn = this.getEntryNoByOrgAndCycle(orgid, cycleId);
        if (oldEn != null) {
            //throw new RuntimeException("存在相同的考核周期和考核组织！");
        }
        return saveEntryNo(null, cycleId, orgid, person);
    }

    public EntryNo updateEntryNo(String entryno, String cycleId, String orgid, Person person) {
        EntryNo oldEn = this.getEntryNoByOrgAndCycle(orgid, cycleId);
        if (oldEn != null && !oldEn.getEntrynoId().equals(entryno)) {
            //throw new RuntimeException("存在相同的考核周期和考核组织！");
        }
        return saveEntryNo(entryno, cycleId, orgid, person);
    }

    private EntryNo saveEntryNo(String entryno, String cycleId, String orgid, Person person) {

        return saveEntryNo(entryno, cycleId, orgid, person, "0");
    }

    private EntryNo saveEntryNo(String entryno, String cycleId, String orgid, Person person, String appNode) {

        EntryNo entryNo = null;
        if (StringUtils.isNotBlank(entryno)) {
            entryNo = EntryNo.dao.findById(entryno);
            if (entryNo != null && (StringUtils.isBlank(entryNo.getEntrynoAppnode()) || "0".equals(entryNo.getEntrynoAppnode()))) {
                entryNo.setEntrynoCycleid(cycleId);
                entryNo.setEntrynoCyclename(Cycle.dao.findById(cycleId).getCycleName());
                entryNo.setEntrynoOrgid(orgid);
                entryNo.setEntrynoOrgname(orgService.getOrgById(orgid).getOrgName());
                entryNo.setEntrynoCreatetime(Tool.getCurrTime());
                entryNo.setEntrynoCreatorid(person.getId());
                entryNo.setEntrynoCreatorname(person.getName());

                entryNo.update();

            }
            return entryNo;
        }

        entryNo = new EntryNo();
        entryNo.setEntrynoId(UUID.randomUUID().toString().replace("-", ""));
        entryNo.setEntrynoCycleid(cycleId);
        entryNo.setEntrynoCyclename(jxCycleService.getCycleNameById(cycleId));
        entryNo.setEntrynoOrgid(orgid);
        entryNo.setEntrynoOrgname(orgService.getOrgById(orgid).getOrgName());
        entryNo.setEntrynoOnline("1");
        entryNo.setEntrynoCreatetime(Tool.getCurrTime());
        entryNo.setEntrynoCreatorid(person.getId());
        entryNo.setEntrynoCreatorname(person.getName());
        entryNo.setEntrynoAppnode(appNode);
        entryNo.save();


        return entryNo;
    }

    @Before(Tx.class)
    public void saveKpi(List<Kpi> list) {
        if (list.size() == 0) return;
        EntryNo entryNo = this.getEntryNoByEntryId(list.get(0).getKpiEntryid());
        boolean beforScoreWf = false;
        String entryNoStatus = entryNo.getEntrynoAppnode();
        if (entryNoStatus.equals("5") || entryNoStatus.equals("7")) {
            beforScoreWf = true;
        }
        //批次号
        List<String> elist = new ArrayList<String>();
        for (Kpi kpi : list) {
            if (StringUtils.isBlank(kpi.getKpiId())) {
                kpi.setKpiId(Tool.uuid());
            }
            if (!elist.contains(kpi.getKpiEntryid())) {
                elist.add(kpi.getKpiEntryid());
            }
            kpi.setKpiIsSelf("2");
            kpi.save();
        }
        int i = 1;
        String lastEntryId = "";
        int lastKpiIndex = 0;
        for (Kpi kpi : list) {//必须跟kpi保存 分开循环， 添加公式方法里面有给同kpi不同评分人加公式的算法
            String entryId = kpi.getKpiEntryid();
            int index = kpi.getKpiIndex();
            if (!(entryId.equals(lastEntryId) && index == lastKpiIndex)) {//同一人的 同kpi不同评分人不计数
                i++;
            }


            lastEntryId = entryId;
            lastKpiIndex = index;
        }
        //更新重复indexNum数据的KpiHead
        for (String s : elist) {
            resetKpiHead(s);
        }

    }

    /**
     * 根据批次号获取该批次所有在自评节点的人员信息
     *
     * @param entry_no
     * @return
     */
    public List<Entry> getSelfEvaluationEntryList(String entry_no) {
        // 1 自评待处理的
        String sql = "select entry_cyclename,entry_khpersonname,entry_khdeptname,entry_orgname,entry_apptime,entry_apptype,entry_id,entry_no  from ct_jx_entry e where e.entry_apptype = '1' and entry_no = ?  order by entry_apptime desc ";

        return Entry.dao.find(sql, entry_no);
    }

    /**
     * 根据批次号获取该批次所有在自评节点的人员信息
     *
     * @param entry_no
     * @return
     */
    public List<Entry> getGradingEntryList(String entry_no) {
        // 1 自评待处理的
        String sql = "select entry_cyclename,entry_khpersonname,entry_khdeptname,entry_apppersonname,entry_orgname,entry_apptime,entry_apptype,entry_id,entry_no  from ct_jx_entry e where e.entry_apptype = '2' and entry_no = ?  order by entry_apptime desc ";

        return Entry.dao.find(sql, entry_no);
    }


//    public List<RatingEntry> getRatingEntryList(String entryNo) {
//        String sql = "select * from ct_jx_ratingentry where ratingentry_entryno = ?";
//        return  RatingEntry.dao.find(sql,entryNo);
//
//
//    }

    //    public void delRatingEntry(String ratingEntryId){
//        String sql = "delete from ct_jx_ratingentry where ratingentry_id = ?";
//        Db.delete(sql,ratingEntryId);
//    }
    public void resetKpiHead(String entryid) {

    }

    private DataBean exceptionReturn(String msg) {
        DataBean dBean = new DataBean();
        dBean.setCode(-1);
        dBean.setMsg("导入失败!" + msg);
        return dBean;
    }

    public void hideManagerData(Kpi kpi) {
        if (kpi == null) return;
        kpi.setKpiScore(null);
        kpi.setKpiInfo(null);
        kpi.setKpiScorelv1(null);
        kpi.setKpiInfolv1(null);
        kpi.setKpiScorelv2(null);
        kpi.setKpiInfolv2(null);
        kpi.setKpiScorelv3(null);
        kpi.setKpiInfolv3(null);
    }

    public void hideManagerData(Entry entry) {
        if (entry == null) return;
        entry.setEntryRating(null);
        entry.setEntryScore(null);
        entry.setEntryRatinglv1(null);
        entry.setEntryScorelv1(null);
        entry.setEntryInfolv1(null);
        entry.setEntryRatinglv2(null);
        entry.setEntryScorelv2(null);
        entry.setEntryInfolv2(null);
        entry.setEntryRatinglv3(null);
        entry.setEntryScorelv3(null);
        entry.setEntryInfolv3(null);
    }
}
