package nckd.jxccl.hr.psms.plugin.form.annualadjust.report;

import kd.bos.algo.DataSet;
import kd.bos.algo.JoinType;
import kd.bos.algo.Row;
import kd.bos.common.enums.EnableEnum;
import kd.bos.context.RequestContext;
import kd.bos.dataentity.entity.DynamicObject;
import kd.bos.dataentity.entity.DynamicObjectCollection;
import kd.bos.entity.report.AbstractReportListDataPlugin;
import kd.bos.entity.report.FastFilter;
import kd.bos.entity.report.ReportQueryParam;
import kd.bos.orm.ORMHint;
import kd.bos.orm.query.QCP;
import kd.bos.orm.query.QFilter;
import kd.bos.servicehelper.QueryServiceHelper;
import kd.bos.servicehelper.model.PermissionStatus;
import kd.sdk.hr.hbp.business.helper.permission.HRPermissionServiceHelper;
import nckd.jxccl.base.common.constant.FormConstant;
import nckd.jxccl.base.common.enums.psms.TypeStateEnum;
import nckd.jxccl.base.common.utils.DateUtil;
import nckd.jxccl.base.common.utils.QueryFieldBuilder;
import nckd.jxccl.hr.psms.common.PositionStructureConstant;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
* 未生成年度调整报表查询插件
* 实体标识：nckd_unannualadjustreort
* @author W.Y.C
* @date 2026/1/2 17:44
* @version 1.0
*/
public class UnAnnualAdjustReportListDataPlugin extends AbstractReportListDataPlugin {
    @Override
    public DataSet query(ReportQueryParam reportQueryParam, Object o) throws Throwable {
        // 构建查询字段
        QueryFieldBuilder queryFieldBuilder = buildQueryFieldBuilder();

        // 构建基础查询条件
        QFilter qFilter = buildBaseQueryFilter();

        // 处理快速过滤条件
        processFastFilter(reportQueryParam, qFilter);

        //其他过滤条件
        processFilter(reportQueryParam, qFilter);
        //权限过滤
        QFilter dataRule = HRPermissionServiceHelper.getDataRule(
                RequestContext.get().getCurrUserId(), "nckd_psmsfile", "unannualadjustquery",
                PermissionStatus.View, new HashMap<>());
        if(dataRule != null){
            qFilter.and(dataRule);
        }

        LocalDateTime localDateTime = DateUtil.beginOfYear(DateUtil.now());
        LocalDateTime lastYear = DateUtil.minusYears(localDateTime, 1);
        LocalDateTime lastBegin = DateUtil.beginOfYear(lastYear);
        LocalDateTime lastEnd = DateUtil.endOfYear(lastYear);


        // 执行基础查询
        DataSet mainDataSet = QueryServiceHelper.queryDataSet(PositionStructureConstant.PERSONPOSFILE_ENTITYID, "unannualadjustquery",
                queryFieldBuilder.buildSelect(), new QFilter[]{qFilter}, null,1000000);
        String[] mainTableFieldNames = mainDataSet.getRowMeta().getFieldNames();
        String[] newMainTableFieldNames = new String[mainTableFieldNames.length + 1];
        System.arraycopy(mainTableFieldNames, 0, newMainTableFieldNames, 0, mainTableFieldNames.length);
        // 添加当前年度
        newMainTableFieldNames[mainTableFieldNames.length] = "'"+localDateTime.getYear()+"' as nckd_currentyear";

        //--------------------- 获取上年度考核结果 begin---------------------
        DataSet mainDataSetCopy = mainDataSet.copy();
        Set<Long> personIds = new HashSet<>();
        while (mainDataSetCopy.hasNext()) {
            Row next = mainDataSetCopy.next();
            Long personId = next.getLong(String.join(".", FormConstant.EMPLOYEE_KEY, FormConstant.ID_KEY));
            personIds.add(personId);
        }
        if(!personIds.isEmpty()) {
            DataSet lastAppraisalYearDateSet = lastAppraisalYear(personIds, DateUtil.toDate(lastBegin), DateUtil.toDate(lastEnd));
            mainDataSet = mainDataSet.join(lastAppraisalYearDateSet, JoinType.INNER)
                    .on(String.join(".", FormConstant.EMPLOYEE_KEY, FormConstant.ID_KEY), String.join(".", FormConstant.NCKD_PERSON, FormConstant.ID_KEY))
                    .select(newMainTableFieldNames, QueryFieldBuilder.create().add(PositionStructureConstant.NCKD_PERFMANAGERENTRY,PositionStructureConstant.NCKD_APPRAISALRESULT).buildSelectArray()).finish();
        }

        //--------------------- 获取上年度考核结果 end---------------------

        return mainDataSet;
    }


    private DataSet lastAppraisalYear(Set<Long> personIds,Date beginYear,Date endYear){
        QueryFieldBuilder queryFieldBuilder = QueryFieldBuilder.create()
                .addIdNumberName(PositionStructureConstant.NCKD_PERSON)
                .add(PositionStructureConstant.NCKD_PERFMANAGERENTRY,PositionStructureConstant.NCKD_APPRAISALRESULT);
        QFilter qFilter = new QFilter(PositionStructureConstant.NCKD_PERSON, QCP.in, personIds)
                .and(new QFilter(String.join(".", PositionStructureConstant.NCKD_PERFMANAGERENTRY, PositionStructureConstant.NCKD_APPRAISALYEAR), QCP.large_equals, beginYear))
                .and(new QFilter(String.join(".", PositionStructureConstant.NCKD_PERFMANAGERENTRY, PositionStructureConstant.NCKD_APPRAISALYEAR), QCP.less_equals, endYear))
                .and(new QFilter(String.join(".", PositionStructureConstant.NCKD_PERFMANAGERENTRY, PositionStructureConstant.NCKD_APPRAISALRESULT), QCP.is_notnull, null))
                .and(new QFilter(String.join(".", PositionStructureConstant.NCKD_PERFMANAGERENTRY, PositionStructureConstant.NCKD_APPRAISALRESULT), QCP.not_equals2, 0));

        return QueryServiceHelper.queryDataSet(this.getClass().getName()+"nckd_perfmanager", "nckd_perfmanager",
                queryFieldBuilder.buildSelect(), new QFilter[]{qFilter}, null,10000);
    }

    /**
     * 构建基础查询条件
     */
    private QFilter buildBaseQueryFilter() {
        LocalDateTime localDateTime = DateUtil.beginOfYear(DateUtil.now());
        //查询当年已执行年度调整的人员
        QueryFieldBuilder queryFieldBuilder = QueryFieldBuilder.create().addIdNumberName(FormConstant.NCKD_PERSON);
        QFilter yearFilter = new QFilter(PositionStructureConstant.NCKD_EXECUTEYEAR, QCP.equals, localDateTime.getYear())
                .and(new QFilter(PositionStructureConstant.NCKD_DISABLE, QCP.equals, EnableEnum.NO.getCode()))
                .and(new QFilter(PositionStructureConstant.NCKD_TYPESTATE, QCP.equals, TypeStateEnum.ANNUAL_ADJUSTMENT.getCode()));
        DynamicObjectCollection query = QueryServiceHelper.query(PositionStructureConstant.PERSONPOSFILE_ENTITYID, queryFieldBuilder.buildSelect(), new QFilter[]{yearFilter});
        List<Long> personIds = new ArrayList<>(query.size());
        for (DynamicObject dynamicObject : query) {
            long personId = dynamicObject.getLong(String.join(".", FormConstant.NCKD_PERSON, FormConstant.ID_KEY));
            personIds.add(personId);
        }
        QFilter qFilter = new QFilter(FormConstant.IS_PRIMARY, QCP.equals, EnableEnum.YES.getCode())
                .and(FormConstant.IS_SEQLATESTRECORD, QCP.equals, EnableEnum.YES.getCode())
                .and(FormConstant.IS_DELETED, QCP.equals, EnableEnum.NO.getCode())
                .and(String.join(".", FormConstant.ASSIGNMENT, FormConstant.IS_PRIMARY), QCP.equals, EnableEnum.YES.getCode())
                .and(String.join(".", FormConstant.ASSIGNMENT, FormConstant.IS_DELETED), QCP.equals, EnableEnum.NO.getCode())
                .and(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID, PositionStructureConstant.NCKD_DISABLE), QCP.equals, EnableEnum.NO.getCode())
                .and(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID, PositionStructureConstant.NCKD_ISCURRENTNEWEST), QCP.equals, EnableEnum.YES.getCode())
                //在岗
                .and(String.join( ".", FormConstant.POS_STATUS, FormConstant.POST_STATE_CLS, FormConstant.NUMBER_KEY),QCP.equals,"1010_S")
                //有初定的人员
                .and(new QFilter(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID+"init", PositionStructureConstant.NCKD_FIRSTRANK), QCP.equals, EnableEnum.YES.getCode()))
                //初定时间不等于当年
                .and(new QFilter(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID+"init", PositionStructureConstant.NCKD_EXECUTEYEAR), QCP.not_equals2, localDateTime.getYear()))


                .and(QFilter.join(FormConstant.EMPLOYEE_KEY, String.join(".", FormConstant.HRPI_PERPROTITLE, FormConstant.EMPLOYEE_KEY), new QFilter(String.join(".", FormConstant.HRPI_PERPROTITLE, "iscompany"),
                        QCP.equals, EnableEnum.YES.getCode()),
                ORMHint.JoinHint.LEFT, Boolean.FALSE))
                .and(QFilter.join(FormConstant.EMPLOYEE_KEY, String.join(".", FormConstant.HRPI_PEROCPQUAL, FormConstant.EMPLOYEE_KEY), new QFilter(String.join(".", FormConstant.HRPI_PEROCPQUAL, "ismajor"),
                                QCP.equals, EnableEnum.YES.getCode()),
                        ORMHint.JoinHint.LEFT, Boolean.FALSE))
                .and(QFilter.join(FormConstant.EMPLOYEE_KEY, String.join(".", FormConstant.HRPI_PEREDUEXP, FormConstant.EMPLOYEE_KEY), new QFilter(String.join(".", FormConstant.HRPI_PEREDUEXP, "ishighestdegree"),
                                QCP.equals, EnableEnum.YES.getCode()),
                        ORMHint.JoinHint.LEFT, Boolean.FALSE));

        //当年还未年度调整的人员
        if(!personIds.isEmpty()) {
            qFilter.and(new QFilter(FormConstant.EMPLOYEE_KEY, QCP.not_in, personIds));
        }

        return qFilter;
    }


    /**
     * 处理快速过滤条件
     */
    private void processFastFilter(ReportQueryParam reportQueryParam, QFilter qFilter) {
        FastFilter fastFilter = reportQueryParam.getFilter().getFastFilter();
        if (fastFilter != null) {
            List<Map<String, List<Object>>> fastFilterList = fastFilter.getFastFilter();
            for (Map<String, List<Object>> stringListMap : fastFilterList) {
                //nckd_empnumfastfilter转为employee.empnumber，nckd_namefastfilter转换为employee.name，转换后添加到fields中
                List<Object> fieldList = stringListMap.get("FieldName");
                List<Object> valueList = stringListMap.get("Value");
                String[] fields = new String[fieldList.size()];
                for (int i = 0; i < fieldList.size(); i++) {
                    fields[i] = fieldList.get(i).toString()
                            .replace("nckd_empnumfastfilter", "employee.empnumber")
                            .replace("nckd_namefastfilter", "employee.name");
                }
                //valueList转到values
                String[] values = new String[valueList.size()];
                for (int i = 0; i < valueList.size(); i++) {
                    values[i] = valueList.get(i).toString();
                }
                qFilter.and(QFilter.ftlike(values, fields));
            }
        }
    }

    /**
     * 处理过滤条件
     */
    private void processFilter(ReportQueryParam reportQueryParam, QFilter qFilter) {
        List<QFilter> qFilters = reportQueryParam.getFilter().getQFilters();
        for (QFilter filter : qFilters) {
            //由于页面命名限制不允许配置对应数据库字段（例如：position.id的格式），这里只能手动转换为数据库实际的字段
            String property = filter.getProperty();
            if ("nckd_positionfilter.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.POSITION_KEY, FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if("nckd_orgfilter.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.COMPANY_KEY, FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if("nckd_joblevelhrffilter.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID, PositionStructureConstant.NCKD_JOBLEVELHR,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if("nckd_begindatefilter".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID, PositionStructureConstant.NCKD_BEGINDATE),filter.getCP(),filter.getValue()));
            }
            if ("nckd_secondorg.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.ADMINORG,FormConstant.NCKD_SECONDORG,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_thirdorg.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.ADMINORG,FormConstant.NCKD_THIRDORG,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_fourthorg.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.ADMINORG,FormConstant.NCKD_FOURTHORG,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_fifthorg.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.ADMINORG,FormConstant.NCKD_FIFTHORG,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_sixthorg.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.ADMINORG,FormConstant.NCKD_SIXTHORG,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_position.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", FormConstant.POSITION_KEY,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_jobseq.id".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", PositionStructureConstant.PERSONPOSFILE_ENTITYID,PositionStructureConstant.NCKD_JOBSEQHR,FormConstant.ID_KEY),filter.getCP(),filter.getValue()));
            }
            if ("nckd_begindate".equalsIgnoreCase(property)){
                qFilter.and(new QFilter(String.join(".", "nckd_personposfileinit",PositionStructureConstant.NCKD_BEGINDATE),filter.getCP(),filter.getValue()));
            }
        }
    }

    /**
     * 构建查询字段
     */
    private QueryFieldBuilder buildQueryFieldBuilder() {
        return QueryFieldBuilder.create()
                .add(FormConstant.ID_KEY)
                .add(FormConstant.EMPLOYEE_KEY)
                .addGroup(new String[]{FormConstant.EMPLOYEE_KEY},FormConstant.ID_KEY, FormConstant.EMP_NUMBER_KEY, FormConstant.NAME_KEY)
                .addGroup(new String[]{FormConstant.ADMINORG},
                        FormConstant.NCKD_FIRSTORG,
                        FormConstant.NCKD_SECONDORG,
                        FormConstant.NCKD_THIRDORG,
                        FormConstant.NCKD_FOURTHORG,
                        FormConstant.NCKD_FIFTHORG,
                        FormConstant.NCKD_SIXTHORG)
                .add("nckd_personposfileinit",PositionStructureConstant.NCKD_BEGINDATE)
                .addGroup(new String[]{PositionStructureConstant.PERSONPOSFILE_ENTITYID},
                        PositionStructureConstant.NCKD_POSITIONHR,
                        PositionStructureConstant.NCKD_JOBSEQHR,
                        PositionStructureConstant.NCKD_PROTITLELEVEL,
                        PositionStructureConstant.NCKD_OCPQUALLEVEL,
                        PositionStructureConstant.NCKD_DIPLOMA,
                        PositionStructureConstant.NCKD_ALLSUMSCORE,
                        PositionStructureConstant.NCKD_BEGINDATE,
                        PositionStructureConstant.NCKD_JOBLEVELHR,
                        PositionStructureConstant.NCKD_PERSON,
                        PositionStructureConstant.NCKD_DEP,
                        PositionStructureConstant.NCKD_ALLOWANCERANKMARK,
                        PositionStructureConstant.NCKD_ALLOWANCERANKSEL,
                        PositionStructureConstant.NCKD_COEFFICIENT,
                        PositionStructureConstant.NCKD_CURRENTPOSTSALARY,
                        PositionStructureConstant.NCKD_POSTALLOWANCE,
                        PositionStructureConstant.NCKD_TYPESTATE,
                        PositionStructureConstant.NCKD_APPRAISALRESULT,
                        PositionStructureConstant.NCKD_RANKSCORE,
                        PositionStructureConstant.NCKD_JOBSTATUSSCORE,
                        PositionStructureConstant.NCKD_DIPLOMASCORE,
                        PositionStructureConstant.NCKD_ORGINSSCORE,
                        PositionStructureConstant.NCKD_SUMSCORE,
                        PositionStructureConstant.NCKD_RESULTSCORE,
                        PositionStructureConstant.NCKD_LYRCONTRIBSCORE,
                        PositionStructureConstant.NCKD_YEARSCORESUMA,
                        PositionStructureConstant.NCKD_YEARSCORESUMB,
                        PositionStructureConstant.NCKD_YEARSCORESUMC,
                        PositionStructureConstant.NCKD_YEARSCORESUMD,
                        PositionStructureConstant.NCKD_YEARSCORESUME,
                        PositionStructureConstant.NCKD_YEARSCORESUMF,
                        PositionStructureConstant.NCKD_YEARSCORESUMG,
                        PositionStructureConstant.NCKD_YEARSCORESUMH,
                        PositionStructureConstant.NCKD_YEARSCORESUMI,
                        PositionStructureConstant.NCKD_ALLYEARSCORESUM

                )
                .addGroup(new String[]{FormConstant.HRPI_PERPROTITLE}, FormConstant.PROLEVEL_KEY)
                .addGroup(new String[]{FormConstant.HRPI_PEROCPQUAL}, FormConstant.QUALIFICATION_KEY)
                .addGroup(new String[]{FormConstant.HRPI_PEREDUEXP}, FormConstant.EDUCATION_KEY)
                .add(FormConstant.COMPANY_KEY)
                .addIdNumberName(FormConstant.COMPANY_KEY)
                .add(FormConstant.ADMINORG)
                .addIdNumberName(FormConstant.POSITION_KEY)
                .addGroup(new String[]{FormConstant.HBPM_POSITIONHR}, PositionStructureConstant.NCKD_JOBSEQ)
                .addGroup(new String[]{FormConstant.HBPM_POSITIONHR, PositionStructureConstant.NCKD_JOBSEQ}, FormConstant.NUMBER_KEY);


    }
}
