package nckd.jxccl.hrmp.hbpm.plugin.operate.hr.validator;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import kd.bos.common.enums.EnableEnum;
import kd.bos.dataentity.OperateOption;
import kd.bos.dataentity.entity.DynamicObject;
import kd.bos.dataentity.metadata.IDataEntityProperty;
import kd.bos.entity.ExtendedDataEntity;
import kd.bos.entity.operate.OperateOptionConst;
import kd.bos.entity.operate.result.OperateErrorInfo;
import kd.bos.entity.operate.result.OperationResult;
import kd.bos.entity.validate.AbstractValidator;
import kd.bos.entity.validate.ValidateResult;
import kd.bos.orm.query.QCP;
import kd.bos.orm.query.QFilter;
import kd.hr.hbp.business.servicehelper.HRBaseServiceHelper;
import kd.hr.hbp.common.util.HRObjectUtils;
import kd.hr.hbp.common.util.HRStringUtils;
import nckd.jxccl.hrmp.hbpm.business.hr.service.impl.PositionBillServiceHelper;
import nckd.jxccl.hrmp.hbpm.common.hr.PositionBillConstant;

import java.util.List;
import java.util.Map;

/**
 * 岗位申请单分录校验器
 * @from: kd.hr.homs.opplugin.web.orgbatch.validator.AbsBillOrgSaveValidator
 * @author: jtd
 * @date: 2025/12/23 20:55
 */
public abstract class AbsBillPositionSaveValidator extends AbstractValidator  {
    abstract String getOperationKey();

    @Override
    public void initialize() {
        super.initialize();

        String ignoreBillNoForContent = getOption().getVariableValue(PositionBillConstant.OP_VALIDATOR_SUFFIX_IGNORE, Boolean.FALSE.toString());
        if (Boolean.TRUE.toString().equals(ignoreBillNoForContent)) {
            setAddBillNoForContent(false);
        }
    }

    @Override
    public void validate() {
        HRBaseServiceHelper positionHrServiceHelper = HRBaseServiceHelper.create(PositionBillConstant.HBPM_POSITIONHR);
        ExtendedDataEntity[] entities = getDataEntities();
        List<DynamicObject> addPositionList = Lists.newArrayListWithExpectedSize(entities.length);
        OperateOption operateOption = OperateOption.create();
        OperateOption option = getOption();
        operateOption.mergeValue(option);
        // 跳过系统默认的权限校验，数据、操作权限等
        operateOption.setVariableValue(OperateOptionConst.SKIPCHECKPERMISSION, Boolean.TRUE.toString());
        // 跳过字段值合规性校验
        operateOption.setVariableValue(PositionBillConstant.OP_SKIPMUSTINPUT, Boolean.TRUE.toString());
        Map<Object, ExtendedDataEntity> entityMap = Maps.newHashMapWithExpectedSize(entities.length);

        for(ExtendedDataEntity entity : entities) {
            DynamicObject positionDy = entity.getDataEntity();
            long positionId = positionDy.getLong(String.join("_", PositionBillConstant.NCKD_POSITION_KEY, PositionBillConstant.ID_KEY));
            entityMap.put(positionId, entity);
        }

        for(ExtendedDataEntity entity : entities) {
            DynamicObject positionEntity = entity.getDataEntity();
            long positionId = positionEntity.getLong(String.join("_", PositionBillConstant.NCKD_POSITION_KEY, PositionBillConstant.ID_KEY));
            DynamicObject addPositionDy = PositionBillServiceHelper.getPositionHrDy(positionEntity);
            addPositionDy.set(PositionBillConstant.ID_KEY, positionId);
            addPositionDy.set(PositionBillConstant.BOID_KEY, positionEntity.get(String.join(".", PositionBillConstant.NCKD_POSITION_KEY, PositionBillConstant.BOID_KEY)));
            DynamicObject parentPositionVersionDy = positionEntity.getDynamicObject(PositionBillConstant.NCKD_PARENT);
            if (parentPositionVersionDy != null) {
                long parentOrgBoId = parentPositionVersionDy.getLong(PositionBillConstant.BOID_KEY);
                if (!HRObjectUtils.isEmpty(parentOrgBoId) && parentOrgBoId > 0L) {
                    // 过滤 当前版本 并且 数据版本生效 并且 不是标准岗位
                    // 这是为了避免查出申请单中暂存的岗位，逻辑参考于kd.hr.homs.opplugin.web.orgbatch.validator.AbsBillOrgSaveValidator
                    QFilter qFilter = new QFilter(PositionBillConstant.IS_CURRENT_VERSION, QCP.equals, Boolean.TRUE)
                            .and(PositionBillConstant.DATA_STATUS, QCP.equals, EnableEnum.YES.getCode())
                            .and(PositionBillConstant.ISSTANDARDPOS_KEY, QCP.equals, EnableEnum.NO.getCode())
                            .and(PositionBillConstant.ID_KEY, QCP.equals, parentOrgBoId);
                    DynamicObject currentParentDy = positionHrServiceHelper.loadDynamicObject(qFilter);
                    if (currentParentDy != null) {
                        addPositionDy.set(PositionBillConstant.PARENT_KEY, currentParentDy);
                    }
                }
            }

            String number = addPositionDy.getString(PositionBillConstant.NUMBER_KEY);
            if (HRStringUtils.isNotEmpty(number)) {
                operateOption.setVariableValue(positionId + "coderule_billno_from_initAbstractCodeRule", "coderule_billno_from_init_value_of_operation");
            }

            addPositionList.add(addPositionDy);
            IDataEntityProperty masteridProperty = positionEntity.getDataEntityType().getProperties().get(PositionBillConstant.MASTER_ID);
            positionEntity.getDataEntityState().setBizChanged(masteridProperty.getOrdinal(), false);
        }

        if (!addPositionList.isEmpty()) {
            OperationResult operationResult = PositionBillServiceHelper.executeOperateOnlyValidate(getOperationKey(), addPositionList.toArray(new DynamicObject[0]), operateOption);
            if (operationResult != null && !operationResult.isSuccess()) {
                for(ValidateResult validateError : operationResult.getValidateResult().getValidateErrors()) {
                    for(OperateErrorInfo operateErrorInfo : validateError.getAllErrorInfo()) {
                        Object pkValue = operateErrorInfo.getPkValue();
                        ExtendedDataEntity entity = entityMap.get(pkValue);
                        if (entity != null) {
                            addErrorMessage(entity, operateErrorInfo.getMessage());
                        } else {
                            addErrorMessage(entities[0], operateErrorInfo.getMessage());
                        }
                    }
                }
            }
        }

    }

}
