Bladeren bron

1.费用标准增加额度调整、额度作废、额度同步逻辑

lisheng 1 week geleden
bovenliggende
commit
0b3025c4b3

+ 1 - 0
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/common/ReimAmountSourceTypeEnum.java

@@ -6,6 +6,7 @@ public enum ReimAmountSourceTypeEnum {
     POSITIONCHANGE("positionchange", "岗位变动"),
     JOBLEVELCHANGE("joblevelchange", "职级变动"),
     ER_REIMCTL_NEW("er_reimctl_new", "手工新增"),
+    STANDARDCHANGE("standardchange", "费用标准同步"),
     SYSTEMIMPORT("systemimport", "系统导入");
     private String key ;
 

+ 5 - 0
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/common/constant/LimitRelasetConstant.java

@@ -10,6 +10,11 @@ public interface LimitRelasetConstant extends BillConstant{
      * 费用项目
      */
     String KEY_NCKD_EXPENSEITEM = "nckd_expenseitem";
+    /**
+     * 职级岗位类型
+     */
+    String KEY_NCKD_CLASSTYPE_JOBPOS = "nckd_classtype_jobpos";
+
     /**
      * 职级岗位
      */

+ 69 - 0
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/plugin/form/LimitRelasetAdjustEdit.java

@@ -0,0 +1,69 @@
+package nckd.jimin.jyyy.fi.plugin.form;
+
+import kd.bos.context.RequestContext;
+import kd.bos.dataentity.entity.DynamicObject;
+import kd.bos.form.FormShowParameter;
+import kd.bos.form.events.AfterDoOperationEventArgs;
+import kd.bos.form.events.PreOpenFormEventArgs;
+import kd.bos.form.plugin.AbstractFormPlugin;
+import kd.bos.servicehelper.BusinessDataServiceHelper;
+import kd.bos.servicehelper.operation.SaveServiceHelper;
+import nckd.jimin.jyyy.fi.common.constant.LimitRelasetConstant;
+
+import java.math.BigDecimal;
+import java.util.Date;
+import java.util.EventObject;
+import java.util.Optional;
+
+public class LimitRelasetAdjustEdit extends AbstractFormPlugin {
+
+    @Override
+    public void preOpenForm(PreOpenFormEventArgs e) {
+        super.preOpenForm(e);
+    }
+
+    @Override
+    public void afterCreateNewData(EventObject e) {
+        super.afterCreateNewData(e);
+        FormShowParameter parameter = this.getView().getFormShowParameter();
+        if(parameter.getCustomParams().containsKey("billid")){
+            Object billid = parameter.getCustomParam("billid");
+            if(billid != null){
+                DynamicObject limitRelasetBill = BusinessDataServiceHelper.loadSingle(billid, LimitRelasetConstant.ENTITYID, String.join(",", LimitRelasetConstant.ID, LimitRelasetConstant.KEY_NCKD_AMOUNT));
+                this.getModel().setValue("nckd_limitrelaset", limitRelasetBill);
+            }
+        }
+    }
+
+    @Override
+    public void afterDoOperation(AfterDoOperationEventArgs args) {
+        super.afterDoOperation(args);
+        String operateKey = args.getOperateKey();
+        if(args.getOperationResult() != null && args.getOperationResult().isSuccess()){
+            if("confirm".equals(operateKey)){
+                DynamicObject limitRelasetBillF7 = (DynamicObject)this.getModel().getValue("nckd_limitrelaset");
+                BigDecimal amount = (BigDecimal)this.getModel().getValue("nckd_amount");
+                BigDecimal preAmount = limitRelasetBillF7.getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
+                if(limitRelasetBillF7 != null){
+                    DynamicObject limitRelasetBill = BusinessDataServiceHelper.loadSingle(limitRelasetBillF7.getPkValue(), LimitRelasetConstant.ENTITYID, String.join(",", LimitRelasetConstant.ID, LimitRelasetConstant.KEY_NCKD_AMOUNT));
+                    limitRelasetBill.set(LimitRelasetConstant.KEY_NCKD_AMOUNT, amount);
+                    String message = String.format("额度月额度从%s调整成%s。", Optional.ofNullable(preAmount).orElse(BigDecimal.ZERO).setScale(2, BigDecimal.ROUND_HALF_UP).toPlainString(),
+                            Optional.ofNullable(amount).orElse(BigDecimal.ZERO).setScale(2, BigDecimal.ROUND_HALF_UP).toPlainString());
+                    SaveServiceHelper.save(new DynamicObject[]{ limitRelasetBill });
+                    saveLimitRelasetLog(limitRelasetBillF7.getLong(LimitRelasetConstant.ID),"adjustquota", message);
+                }
+                this.getView().close();
+            }
+        }
+    }
+
+    private void saveLimitRelasetLog(long limitRelasetId, String operate ,String description){
+        DynamicObject limitRelasetOperateInfo = BusinessDataServiceHelper.newDynamicObject("nckd_limitrelasetoperate");
+        limitRelasetOperateInfo.set("nckd_operator", RequestContext.get().getCurrUserId());
+        limitRelasetOperateInfo.set("nckd_operatetime",new Date());
+        limitRelasetOperateInfo.set("nckd_limitrelaset", limitRelasetId);
+        limitRelasetOperateInfo.set("nckd_operate", operate);
+        limitRelasetOperateInfo.set("nckd_description", description);
+        SaveServiceHelper.save(new DynamicObject[]{ limitRelasetOperateInfo });
+    }
+}

+ 174 - 20
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/plugin/form/LimitRelasetList.java

@@ -4,38 +4,68 @@ import com.alibaba.fastjson.JSON;
 import com.alibaba.fastjson.JSONObject;
 import com.kingdee.util.StringUtils;
 import kd.bos.context.RequestContext;
+import kd.bos.dataentity.entity.DynamicObject;
+import kd.bos.entity.EntityMetadataCache;
+import kd.bos.entity.datamodel.ListSelectedRowCollection;
 import kd.bos.entity.operate.result.OperationResult;
-import kd.bos.form.CloseCallBack;
+import kd.bos.form.*;
 import kd.bos.form.events.AfterDoOperationEventArgs;
+import kd.bos.form.events.BeforeDoOperationEventArgs;
 import kd.bos.form.events.ClosedCallBackEvent;
+import kd.bos.form.events.MessageBoxClosedEvent;
+import kd.bos.form.operate.FormOperate;
+import kd.bos.list.BillList;
 import kd.bos.list.plugin.AbstractListPlugin;
+import kd.bos.orm.query.QCP;
+import kd.bos.orm.query.QFilter;
 import kd.bos.schedule.api.JobInfo;
 import kd.bos.schedule.api.JobType;
 import kd.bos.schedule.api.TaskInfo;
 import kd.bos.schedule.form.JobForm;
+import kd.bos.servicehelper.BusinessDataServiceHelper;
+import kd.bos.servicehelper.QueryServiceHelper;
+import kd.bos.servicehelper.operation.SaveServiceHelper;
+import nckd.jimin.jyyy.fi.common.ReimAmountSourceTypeEnum;
+import nckd.jimin.jyyy.fi.common.constant.JobPositionBakBillConstant;
+import nckd.jimin.jyyy.fi.common.constant.LimitRelasetConstant;
 import nckd.jimin.jyyy.fi.plugin.operate.Helper.PersonReimQuotaHelper;
+import nckd.jimin.jyyy.fi.plugin.operate.Helper.PersonReimQuotaVO;
 
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Optional;
-import java.util.UUID;
+import java.math.BigDecimal;
+import java.util.*;
+import java.util.stream.Collectors;
 
 public class LimitRelasetList extends AbstractListPlugin {
-    private static final String OP_REFRESH_ALLQUOTA = "refresh_allquota";
+    // 额度同步
+    private static final String OP_SYNCQUOTA = "syncquota";
+    // 额度更新
+    private static final String OP_ADJUSTQUOTA = "adjustquota";
 
-    private static final String OP_REFRESH_ALLLEVER = "refresh_alllever";
+    // 额度同步:作废额度回调
+    private static final String COMFIRMCALLBACK_SYNCQUOTA_CANCEL = "comfirmcallback_syncquota_cancel";
+    // 额度同步:同步回调
+    private static final String COMFIRMCALLBACK_SYNCQUOTA_SYNC = "comfirmcallback_syncquota_sync";
 
 
-    private PersonReimQuotaHelper personReimQuotaHelper;
+    // 费用标准作废
+    private static final String OP_CANCEL = "cancel";
 
-    @Override
-    public void initialize() {
-        super.initialize();
-        personReimQuotaHelper = new PersonReimQuotaHelper();
-    }
 
-    protected PersonReimQuotaHelper getPersonReimQuotaHelper() {
-        return Optional.ofNullable(personReimQuotaHelper).orElse(new PersonReimQuotaHelper());
+    @Override
+    public void beforeDoOperation(BeforeDoOperationEventArgs args) {
+        super.beforeDoOperation(args);
+        FormOperate operate = (FormOperate)args.getSource();
+        String operateKey = operate.getOperateKey();
+        BillList billList = (BillList)this.getControl("billlistap");
+        ListSelectedRowCollection selectedRows = billList.getSelectedRows();
+        // 额度同步和变更仅允许选择一条记录
+        if(OP_SYNCQUOTA.equals(operateKey) || OP_ADJUSTQUOTA.equals(operateKey)){
+            if(selectedRows.size() > 1){
+                this.getView().showTipNotification("仅允许选择一条数据进行操作。");
+                args.setCancel( true);
+                return;
+            }
+        }
     }
 
     @Override
@@ -43,17 +73,122 @@ public class LimitRelasetList extends AbstractListPlugin {
         super.afterDoOperation(args);
         String operateKey = args.getOperateKey();
         OperationResult operationResult = args.getOperationResult();
-        if(operationResult != null && !operationResult.isSuccess()){
+        if(operationResult == null || !operationResult.isSuccess() || operationResult.getSuccessPkIds().size() == 0){
+
             return;
         }
-        if ( OP_REFRESH_ALLQUOTA.equals(operateKey)) {
-            dispatch("更新个人额度","updatequota");
+
+        List<Object> successPkIds = operationResult.getSuccessPkIds();
+        if ( OP_ADJUSTQUOTA.equals(operateKey)) {
+            // 打开额度调整界面
+            showUpdateQuota(successPkIds.get(0).toString());
+        }
+
+        if ( OP_SYNCQUOTA.equals(operateKey)) {
+            DynamicObject limitRelasetInfo = BusinessDataServiceHelper.loadSingle(successPkIds.get(0),LimitRelasetConstant.ENTITYID);
+            String status = limitRelasetInfo.getString(LimitRelasetConstant.KEY_STATUS);
+            Map<String, Object> varMap = new HashMap<>();
+            varMap.put("billid", successPkIds.get(0));
+            // 已作废
+            if("I".equals(status)){
+                ConfirmCallBackListener confirmCallBackListener = new ConfirmCallBackListener(COMFIRMCALLBACK_SYNCQUOTA_CANCEL, this);
+                // 设置页面确认框,参数为:标题,选项框类型,回调监听
+                getView().showConfirm(String.format("费用标准%s状态为已作废,额度同步后将作废费用项目%s下的额度信息,请确认是否同步?",
+                                limitRelasetInfo.getString(LimitRelasetConstant.KEY_NUMBER),limitRelasetInfo.getDynamicObject(LimitRelasetConstant.KEY_NCKD_EXPENSEITEM).getString(LimitRelasetConstant.KEY_NAME)),
+                        MessageBoxOptions.YesNo, confirmCallBackListener);
+            }
+            // 已审核
+            else if("C".equals(status)){
+                ConfirmCallBackListener confirmCallBackListener = new ConfirmCallBackListener(COMFIRMCALLBACK_SYNCQUOTA_SYNC, this);
+                // 设置页面确认框,参数为:标题,选项框类型,回调监听
+                getView().showConfirm(String.format("费用标准%s状态为已审核,额度同步后将更新费用项目%s下的额度信息,请确认是否同步?",
+                        limitRelasetInfo.getString(LimitRelasetConstant.KEY_NUMBER),limitRelasetInfo.getDynamicObject(LimitRelasetConstant.KEY_NCKD_EXPENSEITEM).getString(LimitRelasetConstant.KEY_NAME))
+                ,MessageBoxOptions.YesNo, confirmCallBackListener);
+            }else{
+                this.getView().showTipNotification("仅已审核、已作废状态允许进行额度同步。");
+            }
+
         }
 
-        if ( OP_REFRESH_ALLLEVER.equals(operateKey)) {
-            dispatch("更新差旅级别","updatelever");
+        if(OP_CANCEL.equals(operateKey)){
+            successPkIds.stream().forEach(pkId -> saveLimitRelasetLog((Long)pkId, operateKey, "额度作废"));
         }
     }
+    protected void showUpdateQuota(String pkId) {
+        FormShowParameter parameter = new FormShowParameter();
+        parameter.setFormId("nckd_limitrelasetadjust");
+        parameter.getOpenStyle().setShowType(ShowType.Modal);
+        Map<String, Object> customParams = parameter.getCustomParams();
+        customParams.put("billid",pkId);
+        getView().showForm(parameter);
+    }
+
+
+    @Override
+    public void confirmCallBack(MessageBoxClosedEvent event) {
+        super.confirmCallBack(event);
+        String callBackId = event.getCallBackId();
+        if(!MessageBoxResult.Yes.equals(event.getResult())){
+            return;
+        }
+        BillList billList = (BillList)this.getControl("billlistap");
+        ListSelectedRowCollection selectedRows = billList.getSelectedRows();
+        if(selectedRows.size() == 1){
+            Object billid = selectedRows.get(0).getPrimaryKeyValue();
+            PersonReimQuotaHelper personReimQuotaHelper = new PersonReimQuotaHelper();
+
+            DynamicObject limitRelasetInfo = BusinessDataServiceHelper.loadSingle(billid,LimitRelasetConstant.ENTITYID);
+            // 作废
+            if(COMFIRMCALLBACK_SYNCQUOTA_CANCEL.equals(callBackId)){
+                personReimQuotaHelper.doInvalidPersonReim(new QFilter[]{
+                        new QFilter("nckd_limitrelaset", QCP.equals, limitRelasetInfo.getLong(LimitRelasetConstant.ID)),
+                });
+                getView().showSuccessNotification("关闭关联的个人额度成功。");
+                saveLimitRelasetLog(Long.valueOf(billid.toString()), OP_SYNCQUOTA, "额度同步-费用标准废弃后,关闭关联个人额度。");
+            }
+            // 同步
+            if(COMFIRMCALLBACK_SYNCQUOTA_SYNC.equals(callBackId)){
+
+                DynamicObject[] personPositionJobBakArray = getPersonPositionJobBakCol();
+                Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap = personReimQuotaHelper.getLimitRelasetMap();
+
+                String classType = limitRelasetInfo.getString(LimitRelasetConstant.KEY_NCKD_CLASSTYPE_JOBPOS);
+
+                DynamicObject jobPosition = limitRelasetInfo.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS);
+                if(jobPosition == null){
+                    return;
+                }
+                long expenseItemId = limitRelasetInfo.getDynamicObject(LimitRelasetConstant.KEY_NCKD_EXPENSEITEM).getLong(LimitRelasetConstant.ID);
+                long currencyId = limitRelasetInfo.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CURRENCY).getLong(LimitRelasetConstant.ID);
+                BigDecimal quotaAmont = limitRelasetInfo.getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
+
+                for(DynamicObject jobBakInfo : personPositionJobBakArray){
+                    // 职级或者岗位能够匹配
+                    if(("hbjm_joblevelhr".equals(classType) && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW) != null
+                            && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW).getLong(JobPositionBakBillConstant.ID) == jobPosition.getLong(LimitRelasetConstant.ID))
+                            || ("hbpm_positionhr".equals(classType) && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_NEW) != null
+                            && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_NEW).getLong(JobPositionBakBillConstant.ID) == jobPosition.getLong(LimitRelasetConstant.ID))){
+
+                        PersonReimQuotaVO personReimQuotaVO = new PersonReimQuotaVO(
+                                jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID),
+                                jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getLong(JobPositionBakBillConstant.ID),
+                                expenseItemId,
+                                currencyId,
+                                quotaAmont,
+                                ReimAmountSourceTypeEnum.STANDARDCHANGE,
+                                "",
+                                limitRelasetInfo.getString(LimitRelasetConstant.ID));
+                        personReimQuotaHelper.createPersonReimAmount(personReimQuotaVO);
+                        break;
+                    }
+                }
+                getView().showSuccessNotification("个人额度同步成功。");
+                saveLimitRelasetLog(Long.valueOf(billid.toString()), OP_SYNCQUOTA, "额度同步-费用标准额度同步到个人额度。");
+            }
+        }
+    }
+
+
     /**
      * 回调事件,在任务处理完毕后继续后续处理
      */
@@ -107,4 +242,23 @@ public class LimitRelasetList extends AbstractListPlugin {
         // 发布任务,并显示进度
         JobForm.dispatch(jobInfo, this.getView(), closeCallBack);
     }
+
+
+    private void saveLimitRelasetLog(long limitRelasetId, String operate ,String description){
+        DynamicObject limitRelasetOperateInfo = BusinessDataServiceHelper.newDynamicObject("nckd_limitrelasetoperate");
+        limitRelasetOperateInfo.set("nckd_operator", RequestContext.get().getCurrUserId());
+        limitRelasetOperateInfo.set("nckd_operatetime",new Date());
+        limitRelasetOperateInfo.set("nckd_limitrelaset", limitRelasetId);
+        limitRelasetOperateInfo.set("nckd_operate", operate);
+        limitRelasetOperateInfo.set("nckd_description", description);
+        SaveServiceHelper.save(new DynamicObject[]{ limitRelasetOperateInfo });
+    }
+
+    protected DynamicObject[] getPersonPositionJobBakCol() {
+        Set<Long> bakBillIdSet = QueryServiceHelper.query(JobPositionBakBillConstant.ENTITYID, JobPositionBakBillConstant.ID, QFilter.isNotNull(JobPositionBakBillConstant.ID).toArray())
+                .stream()
+                .map(r -> r.getLong(JobPositionBakBillConstant.ID))
+                .collect(Collectors.toSet());
+        return BusinessDataServiceHelper.load(bakBillIdSet.toArray(), EntityMetadataCache.getDataEntityType(JobPositionBakBillConstant.ENTITYID));
+    }
 }

+ 115 - 6
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/plugin/operate/Helper/PersonReimQuotaHelper.java

@@ -1,9 +1,10 @@
 package nckd.jimin.jyyy.fi.plugin.operate.Helper;
 
-import json.JSON;
+import com.alibaba.fastjson.JSON;
 import kd.bos.context.RequestContext;
 import kd.bos.dataentity.OperateOption;
 import kd.bos.dataentity.entity.DynamicObject;
+import kd.bos.entity.EntityMetadataCache;
 import kd.bos.entity.operate.result.OperationResult;
 import kd.bos.exception.KDBizException;
 import kd.bos.logging.BizLog;
@@ -18,10 +19,13 @@ import kd.bos.servicehelper.operation.SaveServiceHelper;
 import kd.fi.gl.util.BigDecimalUtil;
 import nckd.jimin.jyyy.fi.common.ReimAmountSourceTypeEnum;
 import nckd.jimin.jyyy.fi.common.constant.BillTypeConstants;
+import nckd.jimin.jyyy.fi.common.constant.JobPositionBakBillConstant;
+import nckd.jimin.jyyy.fi.common.constant.LimitRelasetConstant;
 import nckd.jimin.jyyy.fi.common.util.CommonUtils;
 
 import java.math.BigDecimal;
 import java.util.*;
+import java.util.stream.Collectors;
 
 public class PersonReimQuotaHelper {
 
@@ -33,7 +37,8 @@ public class PersonReimQuotaHelper {
         BizLog.log(String.format("作废条件范围内的个人额度表,过滤条件为:" + JSON.toJSONString(filterList)));
 
         DynamicObject[] invalidPersonReimArray = BusinessDataServiceHelper.load(BillTypeConstants.ER_REIMBURSEAMOUNT, "auditstatus", filterList);
-
+        String idList = Arrays.stream(invalidPersonReimArray).map(personReim -> personReim.getString("id")).collect(Collectors.joining(";"));
+        BizLog.log("作废的个人额度表数据为:" + idList);
         for(DynamicObject invalidPersonReim : invalidPersonReimArray){
             invalidPersonReim.set("auditstatus","2");
         }
@@ -48,6 +53,10 @@ public class PersonReimQuotaHelper {
         Calendar calendar = Calendar.getInstance();
         String year = String.valueOf(calendar.get(Calendar.YEAR));
         int month = calendar.get(Calendar.MONTH) + 1;
+        // 费用标准同步的下个月生效
+        if(ReimAmountSourceTypeEnum.STANDARDCHANGE.equals(quotaVO.getSourcetype())){
+            month = month+1;
+        }
 
         // 通过[公司、费用类型、人员、币别、年度]判断是否已经创建个人额度表
         DynamicObject queryPersonAmount = QueryServiceHelper.queryOne(BillTypeConstants.ER_REIMBURSEAMOUNT, "id,nckd_sourcetype", new QFilter[]{
@@ -67,7 +76,10 @@ public class PersonReimQuotaHelper {
                 BizLog.log(String.format("个人额度表【%s】已存在,且为手工新增,不予处理!", queryPersonAmount.getString("id")));
                 return;
             }
-            copyModifyPersonReim(personAmountBill,queryPersonAmount.getLong("id"),quotaVO.getAmount(),month);
+            boolean isNeedUpdate = copyModifyPersonReim(personAmountBill, queryPersonAmount.getLong("id"), quotaVO.getAmount(), month);
+            if(!isNeedUpdate){
+                return;
+            }
 
         }else{
             createNewPersonReimAmount(personAmountBill,quotaVO);
@@ -82,6 +94,7 @@ public class PersonReimQuotaHelper {
         personAmountBill.set("auditstatus", "0");
         personAmountBill.set("nckd_sourcetype",quotaVO.getSourcetype().getValue());
         personAmountBill.set("nckd_sourcebillid",quotaVO.getSourcebillid());
+        personAmountBill.set("nckd_limitrelaset",quotaVO.getLimitRelasetId());
 
         OperationResult saveOp = OperationServiceHelper.executeOperate("save", BillTypeConstants.ER_REIMBURSEAMOUNT, new DynamicObject[]{personAmountBill}, OperateOption.create());
         if(!saveOp.isSuccess() || saveOp.getSuccessPkIds().size() == 0){
@@ -94,14 +107,29 @@ public class PersonReimQuotaHelper {
 
     }
 
-    protected void copyModifyPersonReim(DynamicObject personAmountBill, Long copyPersonAmountBillId,BigDecimal amount, int startMonth) {
+    protected boolean copyModifyPersonReim(DynamicObject personAmountBill, Long copyPersonAmountBillId,BigDecimal amount, int startMonth) {
         DynamicObject oriPersonAmount = BusinessDataServiceHelper.loadSingle(copyPersonAmountBillId, BillTypeConstants.ER_REIMBURSEAMOUNT);
-        Set<String> ignoreSet = new HashSet<>(Arrays.asList("id"));
-        DynamicObjectUtils.copy(oriPersonAmount,personAmountBill);
+
+        // 如果月份之后的额度与需要更新的额度相同,则不保存
+        Boolean isNeedUpdate = false;
+        for(int i = startMonth; i <= 12; i++) {
+            if( amount != null && amount.compareTo(oriPersonAmount.getBigDecimal("month" + i)) != 0){
+                isNeedUpdate = true;
+                break;
+            }
+        }
+
+        if(!isNeedUpdate){
+            return false;
+        }
+
+        Set<String> ignoreSet = new HashSet<>(Arrays.asList("id","creator","createtime","modifier","modifytime","auditor","auditdate","nckd_sourcetype","nckd_sourcebillid","nckd_limitrelaset"));
+        DynamicObjectUtils.copy(oriPersonAmount,personAmountBill,ignoreSet);
         // 标准字段
         personAmountBill.set("wbsrcbilltype","er_reimctl_modify");
         personAmountBill.set("wbsrcbillid",oriPersonAmount.getPkValue());
         setPersonAmountData(personAmountBill,amount,startMonth);
+        return true;
     }
 
     protected void createNewPersonReimAmount(DynamicObject personAmountBill , PersonReimQuotaVO  quotaVO){
@@ -189,4 +217,85 @@ public class PersonReimQuotaHelper {
 
         }
     }
+
+
+    public void createQuotaJobleverChange(DynamicObject jobBakInfo, Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap, ReimAmountSourceTypeEnum sourcetype){
+        DynamicObject joblever_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW);
+        for(Map.Entry<Long, Map<Long, List<DynamicObject>>> currencyRow : limitRelasetExpenseItemMap.entrySet()){
+            // 币别ID
+            Long currencyId = currencyRow.getKey();
+            // 费用项目分组
+            Map<Long, List<DynamicObject>> expenseItemGroupMap = currencyRow.getValue();
+
+            for(Map.Entry<Long, List<DynamicObject>> expenseItemRow : expenseItemGroupMap.entrySet()){
+                Long expenseItemId = expenseItemRow.getKey();
+                List<DynamicObject> limitRelasetList = expenseItemRow.getValue();
+
+                Optional<DynamicObject> findJobleverOp = limitRelasetList.stream().filter(r -> joblever_new.getPkValue()
+                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
+                if(findJobleverOp.isPresent()){
+                    BigDecimal quotaAmont = findJobleverOp.get().getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
+                    PersonReimQuotaVO personReimQuotaVO = new PersonReimQuotaVO(
+                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID),
+                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getLong(JobPositionBakBillConstant.ID),
+                            expenseItemId,
+                            currencyId,
+                            quotaAmont,
+                            Optional.ofNullable(sourcetype).orElse(ReimAmountSourceTypeEnum.JOBLEVELCHANGE),
+                            "",
+                            findJobleverOp.get().getString(LimitRelasetConstant.ID));
+                    createPersonReimAmount(personReimQuotaVO);
+                }
+            }
+        }
+    }
+
+    public void createQuotaPositionChange(DynamicObject jobBakInfo,Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum sourcetype){
+        DynamicObject joblever_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW);
+        DynamicObject position_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_NEW);
+        for(Map.Entry<Long, Map<Long, List<DynamicObject>>> currencyRow : limitRelasetExpenseItemMap.entrySet()){
+            // 币别ID
+            Long currencyId = currencyRow.getKey();
+            // 费用项目分组
+            Map<Long, List<DynamicObject>> expenseItemGroupMap = currencyRow.getValue();
+
+            for(Map.Entry<Long, List<DynamicObject>> expenseItemRow : expenseItemGroupMap.entrySet()){
+                Long expenseItemId = expenseItemRow.getKey();
+                List<DynamicObject> limitRelasetList = expenseItemRow.getValue();
+
+                Optional<DynamicObject> findJobleverOp = limitRelasetList.stream().filter(r -> joblever_new.getPkValue()
+                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
+                Optional<DynamicObject> findPositionOp = limitRelasetList.stream().filter(r -> position_new.getPkValue()
+                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
+
+                // 人员岗位发生变化时,如果存在职级的费用标准,则不需要调整额度
+                if(!findJobleverOp.isPresent() && findPositionOp.isPresent()){
+                    BigDecimal quotaAmont = findPositionOp.get().getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
+                    PersonReimQuotaVO personReimQuotaVO = new PersonReimQuotaVO(
+                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID),
+                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getLong(JobPositionBakBillConstant.ID),
+                            expenseItemId,
+                            currencyId,
+                            quotaAmont,
+                            Optional.ofNullable(sourcetype).orElse(ReimAmountSourceTypeEnum.POSITIONCHANGE),
+                            "",
+                            findPositionOp.get().getString(LimitRelasetConstant.ID));
+                    createPersonReimAmount(personReimQuotaVO);
+                }
+            }
+        }
+    }
+
+    public Map<Long, Map<Long, List<DynamicObject>>> getLimitRelasetMap() {
+        Set<Long> bakBillIdSet = QueryServiceHelper.query(LimitRelasetConstant.ENTITYID, LimitRelasetConstant.ID, new QFilter[]{
+                new QFilter(LimitRelasetConstant.KEY_STATUS, QFilter.equals, "C")
+        }).stream().map(r -> r.getLong(JobPositionBakBillConstant.ID)).collect(Collectors.toSet());
+
+        DynamicObject[] limitRelasetCol = BusinessDataServiceHelper.load(bakBillIdSet.toArray(), EntityMetadataCache.getDataEntityType(LimitRelasetConstant.ENTITYID));
+        return Arrays.stream(limitRelasetCol)
+                .collect(Collectors.groupingBy(
+                        r -> r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CURRENCY).getLong(LimitRelasetConstant.ID),
+                        Collectors.groupingBy(r -> r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_EXPENSEITEM).getLong(LimitRelasetConstant.ID)
+                        )));
+    }
 }

+ 21 - 0
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/plugin/operate/Helper/PersonReimQuotaVO.java

@@ -41,6 +41,8 @@ public class PersonReimQuotaVO {
      */
     private String sourcebillid;
 
+    private String limitRelasetId;
+
     public PersonReimQuotaVO(Long userId, Long companyId, Long expenseItemId, Long currencyId, BigDecimal amount, ReimAmountSourceTypeEnum sourcetype) {
         this.userId = userId;
         this.companyId = companyId;
@@ -60,6 +62,17 @@ public class PersonReimQuotaVO {
         this.sourcebillid = sourcebillid;
     }
 
+    public PersonReimQuotaVO(Long userId, Long companyId, Long expenseItemId, Long currencyId, BigDecimal amount, ReimAmountSourceTypeEnum sourcetype, String sourcebillid, String limitRelasetId) {
+        this.userId = userId;
+        this.companyId = companyId;
+        this.expenseItemId = expenseItemId;
+        this.currencyId = currencyId;
+        this.amount = amount;
+        this.sourcetype = sourcetype;
+        this.sourcebillid = sourcebillid;
+        this.limitRelasetId = limitRelasetId;
+    }
+
     public Long getUserId() {
         return userId;
     }
@@ -115,4 +128,12 @@ public class PersonReimQuotaVO {
     public void setSourcebillid(String sourcebillid) {
         this.sourcebillid = sourcebillid;
     }
+
+    public String getLimitRelasetId() {
+        return limitRelasetId;
+    }
+
+    public void setLimitRelasetId(String limitRelasetId) {
+        this.limitRelasetId = limitRelasetId;
+    }
 }

+ 8 - 84
code/jyyy/nckd-jimin-jyyy-fi/src/main/java/nckd/jimin/jyyy/fi/task/PersonReimQuotaSyncTask.java

@@ -39,7 +39,7 @@ public class PersonReimQuotaSyncTask extends AbstractTask implements StopTask {
         // 查询员工额度备份全部数据,
         DynamicObject[] personPositionJobBakArray = getPersonPositionJobBakCol();
         // 查询费用标准配置 按照费用项目分组
-        Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap = getLimitRelasetMap();
+        Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap = personReimQuotaHelper.getLimitRelasetMap();
 
         Arrays.stream(personPositionJobBakArray).forEach(jobBakInfo -> createPersonPotitionJobQuota(jobBakInfo,limitRelasetExpenseItemMap));
 
@@ -55,8 +55,8 @@ public class PersonReimQuotaSyncTask extends AbstractTask implements StopTask {
         if( (jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_OLD) == null && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW) != null)){
             //创建新公司下的个人额度
             logger.info(String.format("人员【%s】新增公司,开始创建公司【%s】下的个人额度。",userNumber,jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getString(JobPositionBakBillConstant.KEY_NAME)));
-            createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
-            createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
+            personReimQuotaHelper.createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
+            personReimQuotaHelper.createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
             return;
         }
              // 2.旧公司不为空  新公司为空
@@ -81,8 +81,8 @@ public class PersonReimQuotaSyncTask extends AbstractTask implements StopTask {
                     new QFilter("company.id", QCP.equals, jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_OLD).getLong(JobPositionBakBillConstant.ID)),
                     new QFilter("user.id", QCP.equals, jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID))
             });
-            createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
-            createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
+            personReimQuotaHelper.createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
+            personReimQuotaHelper.createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum.COMPANYCHANGE);
             return;
         }
 
@@ -90,82 +90,17 @@ public class PersonReimQuotaSyncTask extends AbstractTask implements StopTask {
         if( jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_OLD) != null && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW) != null
             && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_OLD).getLong(JobPositionBakBillConstant.ID) != jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW).getLong(JobPositionBakBillConstant.ID)){
             logger.info(String.format("人员【%s】职级发生变动,开始创建个人额度。",userNumber));
-            createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,null);
+            personReimQuotaHelper.createQuotaJobleverChange(jobBakInfo,limitRelasetExpenseItemMap,null);
         }
 
         // 判断岗位是否发生变更
         if( jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_OLD) != null && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_OLD) != null
             && jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_OLD).getLong(JobPositionBakBillConstant.ID) != jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_NEW).getLong(JobPositionBakBillConstant.ID)){
             logger.info(String.format("人员【%s】岗位发生变动,开始创建个人额度。",userNumber));
-            createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,null);
+            personReimQuotaHelper.createQuotaPositionChange(jobBakInfo,limitRelasetExpenseItemMap,null);
         }
     }
 
-    protected void createQuotaJobleverChange(DynamicObject jobBakInfo, Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap, ReimAmountSourceTypeEnum sourcetype){
-        DynamicObject joblever_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW);
-        for(Map.Entry<Long, Map<Long, List<DynamicObject>>> currencyRow : limitRelasetExpenseItemMap.entrySet()){
-            // 币别ID
-            Long currencyId = currencyRow.getKey();
-            // 费用项目分组
-            Map<Long, List<DynamicObject>> expenseItemGroupMap = currencyRow.getValue();
-
-            for(Map.Entry<Long, List<DynamicObject>> expenseItemRow : expenseItemGroupMap.entrySet()){
-                Long expenseItemId = expenseItemRow.getKey();
-                List<DynamicObject> limitRelasetList = expenseItemRow.getValue();
-
-                Optional<DynamicObject> findJobleverOp = limitRelasetList.stream().filter(r -> joblever_new.getPkValue()
-                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
-                if(findJobleverOp.isPresent()){
-                    BigDecimal quotaAmont = findJobleverOp.get().getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
-                    PersonReimQuotaVO personReimQuotaVO = new PersonReimQuotaVO(
-                        jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID),
-                        jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getLong(JobPositionBakBillConstant.ID),
-                        expenseItemId,
-                        currencyId,
-                        quotaAmont,
-                        Optional.ofNullable(sourcetype).orElse(ReimAmountSourceTypeEnum.JOBLEVELCHANGE));
-                    personReimQuotaHelper.createPersonReimAmount(personReimQuotaVO);
-                }
-            }
-        }
-    }
-
-    protected void createQuotaPositionChange(DynamicObject jobBakInfo,Map<Long, Map<Long, List<DynamicObject>>> limitRelasetExpenseItemMap,ReimAmountSourceTypeEnum sourcetype){
-        DynamicObject joblever_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_JOBLEVEL_NEW);
-        DynamicObject position_new = jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_POSITION_NEW);
-        for(Map.Entry<Long, Map<Long, List<DynamicObject>>> currencyRow : limitRelasetExpenseItemMap.entrySet()){
-            // 币别ID
-            Long currencyId = currencyRow.getKey();
-            // 费用项目分组
-            Map<Long, List<DynamicObject>> expenseItemGroupMap = currencyRow.getValue();
-
-            for(Map.Entry<Long, List<DynamicObject>> expenseItemRow : expenseItemGroupMap.entrySet()){
-                Long expenseItemId = expenseItemRow.getKey();
-                List<DynamicObject> limitRelasetList = expenseItemRow.getValue();
-
-                Optional<DynamicObject> findJobleverOp = limitRelasetList.stream().filter(r -> joblever_new.getPkValue()
-                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
-                Optional<DynamicObject> findPositionOp = limitRelasetList.stream().filter(r -> position_new.getPkValue()
-                        .equals(r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CLASSFIELD_JOBPOS).getPkValue())).findFirst();
-
-                // 人员岗位发生变化时,如果存在职级的费用标准,则不需要调整额度
-                if(!findJobleverOp.isPresent() && findPositionOp.isPresent()){
-                    BigDecimal quotaAmont = findPositionOp.get().getBigDecimal(LimitRelasetConstant.KEY_NCKD_AMOUNT);
-                    PersonReimQuotaVO personReimQuotaVO = new PersonReimQuotaVO(
-                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_USER).getLong(JobPositionBakBillConstant.ID),
-                            jobBakInfo.getDynamicObject(JobPositionBakBillConstant.KEY_NCKD_ORG_NEW).getLong(JobPositionBakBillConstant.ID),
-                            expenseItemId,
-                            currencyId,
-                            quotaAmont,
-                            Optional.ofNullable(sourcetype).orElse(ReimAmountSourceTypeEnum.POSITIONCHANGE));
-                    personReimQuotaHelper.createPersonReimAmount(personReimQuotaVO);
-                }
-            }
-        }
-    }
-
-
-
     protected DynamicObject[] getPersonPositionJobBakCol() {
         Set<Long> bakBillIdSet = QueryServiceHelper.query(JobPositionBakBillConstant.ENTITYID, JobPositionBakBillConstant.ID, QFilter.isNotNull(JobPositionBakBillConstant.ID).toArray())
                 .stream()
@@ -174,16 +109,5 @@ public class PersonReimQuotaSyncTask extends AbstractTask implements StopTask {
         return BusinessDataServiceHelper.load(bakBillIdSet.toArray(), EntityMetadataCache.getDataEntityType(JobPositionBakBillConstant.ENTITYID));
     }
 
-    protected Map<Long, Map<Long, List<DynamicObject>>> getLimitRelasetMap() {
-        Set<Long> bakBillIdSet = QueryServiceHelper.query(LimitRelasetConstant.ENTITYID, LimitRelasetConstant.ID, new QFilter[]{
-                new QFilter(LimitRelasetConstant.KEY_STATUS, QFilter.equals, "C")
-        }).stream().map(r -> r.getLong(JobPositionBakBillConstant.ID)).collect(Collectors.toSet());
-
-        DynamicObject[] limitRelasetCol = BusinessDataServiceHelper.load(bakBillIdSet.toArray(), EntityMetadataCache.getDataEntityType(LimitRelasetConstant.ENTITYID));
-        return Arrays.stream(limitRelasetCol)
-                .collect(Collectors.groupingBy(
-                        r -> r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_CURRENCY).getLong(LimitRelasetConstant.ID),
-                        Collectors.groupingBy(r -> r.getDynamicObject(LimitRelasetConstant.KEY_NCKD_EXPENSEITEM).getLong(LimitRelasetConstant.ID)
-                )));
-    }
+
 }