package com.brilliance.isc.common.liaccv;

import cn.hutool.core.lang.Assert;
import com.brilliance.mda.runtime.mda.IStream;
import com.brilliance.mda.runtime.mda.impl.Argument;
import com.brilliance.mda.runtime.mda.impl.StreamImpl;
import com.brilliance.mda.runtime.mda.util.*;
import org.slf4j.LoggerFactory;
import org.slf4j.Logger;
import com.brilliance.isc.bo.*;
import com.brilliance.isc.common.cache.atpbch.AtpBchCacheService;
import com.brilliance.isc.common.cache.pty.PtyCacheService;
import com.brilliance.isc.common.cbsmod.Cbsget;
import com.brilliance.isc.common.cbsmod.service.CbsmodService;
import com.brilliance.isc.common.cbsmod.service.XrtmodService;
import com.brilliance.isc.common.component.DyncDaoService;
import com.brilliance.isc.common.component.PtsptaToolComponent;
import com.brilliance.isc.common.component.SptDataComponent;
import com.brilliance.isc.common.context.SettleContext;
import com.brilliance.isc.common.context.SpringEnvContext;
import com.brilliance.isc.common.converter.DtoMapper;
import com.brilliance.isc.common.exception.CommonServiceException;
import com.brilliance.isc.common.liaall.service.LiaallService;
import com.brilliance.isc.common.liaccv.service.LiaccvService;
import com.brilliance.isc.common.liaccv.vo.FcdCbbAmtInfoVo;
import com.brilliance.isc.common.liaccv.vo.LiaccvVo;
import com.brilliance.isc.common.liaccv.vo.LiaccvgVo;
import com.brilliance.isc.common.register.liaccv.ILiaccvRegister;
import com.brilliance.isc.common.sysmod.SysmodService;
import com.brilliance.isc.common.transaction.help.LiaallSet;
import com.brilliance.isc.common.transaction.help.TransactionHelpService;
import com.brilliance.isc.common.trnmod.service.TrnmodService;
import com.brilliance.isc.common.util.SettleExceptionUtils;
import com.brilliance.isc.common.util.StringUtils;
import com.brilliance.isc.common.util.Utils;
import com.brilliance.isc.common.vo.*;
import com.brilliance.isc.mda.dao.CbeMapper;
import com.brilliance.isc.mda.dao.FcdMapper;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.util.*;

import static com.brilliance.mda.runtime.mda.Constants.*;

@Service
public class LiaccvServiceImpl implements LiaccvService {

    private static final Logger logger = LoggerFactory.getLogger(LiaccvServiceImpl.class);

    @Autowired
    private LiaallService liaallService;
    @Autowired
    private TrnmodService trnmodService;
    @Autowired
    private CbsmodService cbsmodService;
    @Autowired
    private XrtmodService xrtmodService;
    @Autowired
    private TransactionHelpService transactionHelpService;
    @Autowired
    private PtsptaToolComponent ptsptaToolComponent;
    @Autowired
    private SptDataComponent sptDataComponent;
    @Autowired
    private FcdMapper fcdMapper;
    @Autowired
    private PtyCacheService ptyCacheService;

    @Autowired
    private SysmodService sysmodService;

    @Autowired
    private DyncDaoService dyncDaoService;

    @Autowired
    private Cbsget cbsget;

    @Autowired
    private CbeMapper cbeMapper;

    @Autowired
    private AtpBchCacheService atpBchCacheService;

    @Override
    public void assertLiaccv(LiaccvVo liaccvVo) {
        //! assserts Liaccv; parstm has to be filled before call
        //! only called by assertliaall
        //保证金注册
        liaccvRegister(liaccvVo);
        this.checkLiaccvChange(liaccvVo);
        logger.info("本次试算开始计算mac值");
        String mac = calcMac(liaccvVo);
        logger.info("最新的mac值{},oldmac值{}", mac, liaccvVo.getMacold());
        if (mac.equals(liaccvVo.getMacold())) {
            logger.info("两次mac值计算结果一样，本次试算直接返回");
            return;
        }
        //后手交易根据注册信息和FCD,CBB,CBE拿前手数据,组Liaccvg
        if (StringUtils.isEmpty(liaccvVo.getOldredflg())) {
            getold(liaccvVo);
            liaccvVo.setOldredflg("X");
        }
        SimpleModuleVo cancelModule = getLiaallSet().getCancelModule();
        if (cancelModule == null) {
            liaccvVo.setCanflg(NULLSTR);
        } else {
            if (liaallService.isSameObject(Utils.toJson(cancelModule), liaccvVo.getObjmodpath())) {
                liaccvVo.setCanflg("X");
                liaccvVo.setChgamt(Decimals.add(liaccvVo.getOldamt().negate(), liaccvVo.getOldresamt()));
            } else {
                liaccvVo.setCanflg("");
            }
        }
        //非注销逻辑
        if (!"X".equals(liaccvVo.getCanflg())) {
            // set change amount
            String ccvrol = liaallService.liaallParGet("CCV", "ROL");
            logger.info("assertLiaccv获取ccvrol:{},参数CCV+ROL", ccvrol);
            String chgmod = NULLSTR;
            if (MdaUtils.isEmpty(ccvrol)) {
                liaccvVo.setChgamt(new BigDecimal(Optional.ofNullable(liaallService.liaallParGet("CCV", "AMT")).orElseGet(() -> "0")));
            } else {
                liaccvVo.setNewrol(ccvrol);
                liaccvVo.setChgamt(new BigDecimal(Optional.ofNullable(liaallService.liaallParGet("CCV", "AMT")).orElseGet(() -> "0")));
                chgmod = liaallService.liaallParGet("CCV", "MOD");
                logger.info("assertLiaccv获取chgmod:{}chgamt:{},参数CCV+MOD,路径:{}", chgmod, liaallService.liaallParGet("CCV", "AMT"), liaccvVo.getObjmodpath());
                if (MdaUtils.isEmpty(liaccvVo.getObjmodpath())) {
                    liaccvVo.setObjmodpath(chgmod);
                }
                if (!liaallService.isSameObject(chgmod, liaccvVo.getObjmodpath())) {
                    SettleExceptionUtils.sysDump("Old Cash cover found for " + liaccvVo.getObjmodpath() + ".\nThus LIACCV not able to handle change for " + chgmod + ".");
                }
            }
            chgmod = liaallService.liaallParGet("CCVRES", "MOD");
            logger.info("assertLiaccv获取chgmod:{}chgamt:{},参数CCVRES+MOD,路径:{}", chgmod, liaallService.liaallParGet("CCV", "AMT"), liaccvVo.getObjmodpath());

            if (!MdaUtils.isEmpty(chgmod)) {
                liaccvVo.setChgresamt(new BigDecimal(Optional.ofNullable(liaallService.liaallParGet("CCVRES", "AMT")).orElseGet(() -> "0")));
                if (MdaUtils.isEmpty(liaccvVo.getObjmodpath())) {
                    liaccvVo.setObjmodpath(chgmod);
                }

                String transName = SettleContext.getTransName();
                SimpleModuleVo simpleModuleVo = Utils.toObject(SimpleModuleVo.class, liaccvVo.getObjmodpath());
                String objinr = simpleModuleVo.getObjinr();
                if (!StringUtils.isEmpty(objinr) && ("POP".equalsIgnoreCase(transName.substring(3, transName.length())) || "PCR".equalsIgnoreCase(transName.substring(3, transName.length())))) {
                    logger.info("无需校验ccv");
                } else {
                    if (!liaallService.isSameObject(chgmod, liaccvVo.getObjmodpath())) {
                        throw new RuntimeException("Old Cash cover found for " + liaccvVo.getObjmodpath() + ".\nThus LIACCV not able to handle change for " + chgmod + ".");
                    }
                }
            }
        }
        // ensure that all forward contracts are locked
        for (LiaccvgVo item : liaccvVo.getLiaccvg()) {
            //适用于保证金调整业务，修改了amt金额，需要重算保证金金额和比例
            item.setConcur(liaccvVo.getConcur());
            calcCcdflgbut(item);
            calcRate(liaccvVo, item);
            calcCovAmts(item);
        }
        logger.info("assertLiaccv,判断chgresamt:{}+Oldresamt:{}之和是否大于0", liaccvVo.getChgresamt(), liaccvVo.getOldresamt());
        // if change amounts excceeding old amounts, only book out old amounts
        if (MdaUtils.compareTo(Decimals.add(liaccvVo.getChgresamt(), liaccvVo.getOldresamt()), 0) < 0) {
            liaccvVo.setChgresamt(liaccvVo.getOldresamt().negate());
        }
        logger.info("assertLiaccv,判断chgamt:{}+Oldamt:{}之和是否大于0", liaccvVo.getChgamt(), liaccvVo.getOldamt());
        if (MdaUtils.compareTo(Decimals.add(liaccvVo.getChgamt(), liaccvVo.getOldamt()), 0) < 0) {
            liaccvVo.setChgamt(liaccvVo.getOldamt().negate());
        }
        //重新计算金额和实收比例
        calcTotcovamt(liaccvVo);
        calcRelcshpct(liaccvVo);
        calcPctresamt(liaccvVo);
        calcNewamt(liaccvVo);
        liaccvVo.setAddinf(getAddinf(liaccvVo));
        liaccvVo.setMacold(calcMac(liaccvVo));
        if (StringUtils.isEmpty(liaccvVo.getObjmodpath())) {
            liaccvVo.setObjmodpath(Utils.toJson(SimpleModuleVo.buildModule(liaccvVo.getRec())));
        }
        //获取ccvid,避免保证金重复 适用于保证金调整业务
        for (int i = 0; i < liaccvVo.getLiaccvg().size(); i++) {
            LiaccvgVo liaccvgVo = liaccvVo.getLiaccvg().get(i);
            if ("Y".equals(liaccvgVo.getNewFlag()) && StringUtils.isEmpty(liaccvgVo.getCcvid())) {
                liaccvgVo.setCcvid(calculateCcvid(liaccvVo.getLiaccvg(), liaccvgVo.getCur()));
            }
        }
    }

    /**
     * source:liaccv.0000.script
     */
    public void storeCCV(LiaccvVo liaccv) {
        if (StringUtils.isEmpty(liaccv.getObjmodpath())) {
            logger.info("保证金存盘objmodpath为空,不会保存直接返回");
            return;
        }
        SimpleModuleVo linkMoudle = Utils.toObject(SimpleModuleVo.class, liaccv.getObjmodpath());
        String objinr = linkMoudle.getObjinr();
        String objtyp = linkMoudle.getObjtyp();
        if (StringUtils.isEmpty(objinr) || StringUtils.isEmpty(objtyp)) {
            throw new CommonServiceException("linkModule ObjInr或者objtyp 不能为空");
        }
        Map<String, Object> maps = dyncDaoService.dyncReadByInr(objtyp, objinr);
        // store change of reserved amount if any (even in temporary settlement)
        logger.info("storeCCV,判断条件chgresamt:{}", liaccv.getChgresamt());
        if (MdaUtils.compareTo(liaccv.getChgresamt(), 0) != 0) {
            logger.info("storeCCV-cbsTrnStore,参数MAXAMT+CCVRESAMT+today:{},getConcur:{},getChgresamt:{},nam:Reserved amount for cash cover changed,objmod:{},gettrninr:{}", Dates.today(), liaccv.getConcur(), liaccv.getChgresamt(), Utils.toJson(linkMoudle), transactionHelpService.getTrninr());
            trnmodService.cbsTrnStore("MAXAMT", "CCVRESAMT", Dates.today(), liaccv.getConcur(), liaccv.getChgresamt(), "Reserved amount for cash cover changed", linkMoudle, transactionHelpService.getTrninr());
        }
        // store change of contract amount if any
        if (MdaUtils.compareTo(liaccv.getChgamt(), 0) != 0) {
            // if old balance is set in different currency, remove old amount first
            if (!MdaUtils.isEmpty(liaccv.getOldcur()) && !MdaUtils.isEmpty(liaccv.getOldamt()) && MdaUtils.compareTo(liaccv.getOldcur(), liaccv.getConcur()) != 0) {
                logger.info("storeCCV-cbsTrnStore,参数MAXAMT+CCVAMT+today:{},getOldcur:{},getOldamt:{},nam:cancel due to currency change,objmod:{},gettrninr:{}", Dates.today(), liaccv.getOldcur(), liaccv.getOldamt().negate(), Utils.toJson(linkMoudle), transactionHelpService.getTrninr());
                trnmodService.cbsTrnStore("MAXAMT", "CCVAMT", Dates.today(), liaccv.getOldcur(), liaccv.getOldamt().negate(), "cancel due to currency change", linkMoudle, transactionHelpService.getTrninr());
            }
        }
        /**
         CbsTrnStore( "MAXAMT", "CCVAMT", Today, CONCUR, CHGAMT, GetText( 'L0000015', TAB, CSHPCT ), $objmod )
         **/
        Cbe cbe = new Cbe();
        cbe.setXrfcur(NULLSTR);
        cbe.setExtid("CCVAMT");
        cbe.setCbt("MAXAMT");
        cbe.setTrntyp("TRN");
        cbe.setTrninr(transactionHelpService.getTrninr());
        cbe.setDat(Dates.today());
        cbe.setCur(liaccv.getConcur());
        cbe.setAmt(liaccv.getChgamt());
        cbe.setNam(Strings.getText("Cover changed,the Percent:$1$2", TAB, liaccv.getRelcshpct()));
        if (MdaUtils.compareTo(liaccv.getRelcshpct(), 10000) >= 0) {
            liaccv.setRelcshpct(new BigDecimal("9999"));
        }
        cbe.setNompct(liaccv.getRelcshpct());
        logger.info("storeCCV-Cbe,取值Trninr:{},today:{},getConcur():{},getChgamt:{},getRelcshpct:{},getRelcshpct:{}", transactionHelpService.getTrninr(), Dates.today(), liaccv.getConcur(), liaccv.getChgamt(), liaccv.getRelcshpct(), liaccv.getRelcshpct());

        cbsmodService.cbsStoreEntry(cbe, linkMoudle);
        // store changes of cash cover amounts
        int gridcnt = 0;
        if (liaccv != null && liaccv.getLiaccvg().size() > 0) {
            logger.info("storeCCV,判断条件liaccv.getLiaccvg().size():{}", liaccv.getLiaccvg().size());
            gridcnt = liaccv.getLiaccvg().size();
        }
        String conref = NULLSTR;
        for (int i = 0; i < gridcnt; i++) {
            Assert.notNull(liaccv);
            LiaccvgVo liaccvg = liaccv.getLiaccvg().get(i);
            logger.info("storeCCV,Acplia获取行数:{},liaccvg:{}", i, liaccvg.toString());
            logger.info("storeCCV,Acplia获取objtyp:{},objinr:{},objmodpath:{}", objtyp, objinr, liaccv.getObjmodpath());
            logger.info("storeCCV,Acplia获取amt:{},cur:{}", liaccvg.getAmt(), liaccvg.getCur());
            if (MdaUtils.compareTo(liaccvg.getAmt(), 0) != 0) {
                // set ACPLIA\\CBE
                liaccvg.getAcplia().getCbe().setObjtyp(objtyp);
                liaccvg.getAcplia().getCbe().setObjinr(objinr);
                liaccvg.getAcplia().setObjmod(liaccv.getObjmodpath());
                liaccvg.getAcplia().setCbtpfx("CCV");
                liaccvg.getAcplia().getCbe().setDat(Dates.today());
                liaccvg.getAcplia().getCbe().setAmt(liaccvg.getAmt());
                liaccvg.getAcplia().getCbe().setCur(liaccvg.getCur());
                Fcd fcd = null;
                if (!MdaUtils.isEmpty(liaccvg.getFcdinr())) {
                    //Platform.cacheDbRead(this.getFcdgrp().getRec(),this.getLiaccvg().getElement(i).getFcdinr(),"INR");
                    fcd = new Fcd();
                    logger.info("storeCCV,fcd获取fcdinr:{},fcdownref:{}", liaccvg.getFcdinr(), fcd.getOwnref());
                    fcd.setInr(liaccvg.getFcdinr());
                    fcd = fcdMapper.selectByPrimaryKey(fcd);
                    // set the suffix to nam to be able to find forward contract again. The "$1 )" at the end must not be changed at translation
                    liaccvg.getAcplia().setNamsfx(Strings.getText("(using $1 )", fcd.getOwnref()));
                } else {
                    liaccvg.getAcplia().setNamsfx(Strings.getText("(using $1 )", liaccvg.getOwnref()));
                }
                // store entry
                setAcpliaCbeExtId(liaccv, i);
                logger.info("storeCCV,判断amt:{}是否大于0", liaccvg.getAmt());
                if (MdaUtils.compareTo(liaccvg.getAmt(), 0) > 0) {
                    cbsTrnStoreCcv("CCVIN", liaccvg.getAcplia().getCbe().getExtid(), Dates.today(), liaccvg.getCur(), liaccvg.getAmt(), "CCV inbooking" + liaccvg.getAcplia().getNamsfx(), liaccvg.getAcc(), liaccvg.getAcplia().getCbe().getAcc2(), transactionHelpService.getTrninr(), linkMoudle);
                } else {
                    cbsTrnStoreCcv("CCVOUT", liaccvg.getAcplia().getCbe().getExtid(), Dates.today(), liaccvg.getCur(), liaccvg.getAmt().negate(), "Cash cover used" + liaccvg.getAcplia().getNamsfx(), liaccvg.getAcc(), liaccvg.getAcplia().getCbe().getAcc2(), transactionHelpService.getTrninr(), linkMoudle);
                }
                // if forward contract store forward contract information
                logger.info("storeCCV,判断fcdinr:{}是否为空", liaccvg.getFcdinr());
                if (!MdaUtils.isEmpty(liaccvg.getFcdinr()) && fcd != null) {
                    conref = (String) maps.get("ownref");
                     /*if( ctx.getErrorCode() != 0 )
                    {
                        conref = ctx.absGet(Setmod.class).getRef();
                    }*/
                    fcd.setRegref(conref);
                    fcdMapper.updateByPrimaryKeySelective(fcd);
                    // do not use  CbsTrnStore as we have to store target amount in CBS aswell
                   /* if( MdaUtils.isEmpty(this.getLiaccvg().getElement(i).getCsh().getRegref()) )
                    {
                        this.getLiaccvg().getElement(i).getCsh().setRegref( conref);
                    }*/
                    /**
                     //用trn/inr来代替
                     LIACCVG( $i )\\csh\\PNTINR = GetContent( "\\\\TRNMOD\\\\TRN\\\\INR" )
                     $ERR = ErrorCode
                     LIACCVG( $i )\\CSH\\PNTTYP = "TRN"
                     if IsEmpty( LIACCVG( $i )\\csh\\PNTINR ) then
                     LIACCVG( $i )\\csh\\PNTINR = GetContent( "\\\\SYSMOD\\\\SPT\\\\INR" )
                     $ERR = ErrorCode
                     LIACCVG( $i )\\CSH\\PNTTYP = "SPT"
                     endif
                     **/
                    /**
                     if not IsEmpty( \\LIAALL\\LIACCV\\OBJMODPATH ) then
                     LIACCVG( $i )\\csh\\PNTINR = RecGetInr( GetModule( \\LIAALL\\LIACCV\\OBJMODPATH ) )
                     LIACCVG( $i )\\CSH\\PNTTYP = Mid( \\LIAALL\\LIACCV\\OBJMODPATH, 1, 3 )
                     else
                     LIACCVG( $i )\\csh\\PNTINR = RecGetInr( \\LIAALL\\GRP )
                     LIACCVG( $i )\\CSH\\PNTTYP = Mid( GetFramename, 1, 2 ) + "D"
                     endif
                     **/
                    //Platform.sdbUpdate(this.getLiaccvg().getElement(i).getCsh());
                    cbe = new Cbe();
                    cbe.setExtid("AMT1");
                    cbe.setCbt("UTLAMT");
                    cbe.setTrntyp("TRN");
                    cbe.setTrninr(transactionHelpService.getTrninr());
                    cbe.setDat(Dates.today());
                    cbe.setCur(liaccvg.getCur());
                    cbe.setAmt(liaccvg.getAmt());
                    cbe.setXrfcur(xrtmodService.sysiso());
                    cbe.setXrfamt(xrtmodService.basCurEqu(cbe.getCur(), cbe.getAmt(), Dates.today()));
                    cbe.setNam(Strings.getText("$1 hold", conref));
                    logger.info("storeCCV-Cbe,取值Trninr:{},today:{},getCur():{},getAmt:{},getXrfcur:{},getXrtamt:{},getNam:{}", transactionHelpService.getTrninr(), Dates.today(), liaccvg.getCur(), liaccvg.getAmt(), xrtmodService.sysiso(), xrtmodService.basCurEqu(cbe.getCur(), cbe.getAmt(), Dates.today()), Strings.getText("$1 hold", conref));
                    cbsmodService.cbsStoreEntry(cbe, fcd);
                }
            }
        }
        updateCshpct(liaccv);
    }


    /**
     * source:liaccv.0014.script
     */
    public void cbsTrnStoreCcv(String cbt, String extid, Date dat, String cur, BigDecimal amt, String nam, String argAcc, String argAcc2, String trninr, Object obj) {
        // Own function to store Cash cover in CBS as account info has to be stored in addition to CbsTrnStore function in TRNMOD
        if (!MdaUtils.isEmpty(amt)) {
            Cbe cbe = new Cbe();
            cbe.setExtid(extid);
            cbe.setCbt(cbt);
            cbe.setTrntyp("TRN");
            cbe.setTrninr(trninr);
            cbe.setDat(dat);
            cbe.setCur(cur);
            cbe.setAmt(amt);
            cbe.setNam(nam);
            cbe.setAcc(argAcc);
            cbe.setAcc2(argAcc2);
            logger.info("cbsTrnStoreCcv-Cbe,取值extid:{},cbt:{},trninr:{},dat:{},cur:{},amt:{},nam:{},argAcc:{},argAcc2:{}", extid, cbt, trninr, dat, cur, amt, nam, argAcc, argAcc2);
            cbsmodService.cbsStoreEntry(cbe, obj);
        }

    }


    private void liaccvRegister(LiaccvVo liaccvVo) {
        //! recreates parameter stream by posting all liaallset-methods
        //! The names of all subs setting parameters for LIAALL have to start with liaallset
        //! CAUTION: As the names are loaded at the beginning of transaction, the transaction has to be reloaded.
        getLiaallSet().clearLiaall();
        //按照交易码，获取注册Spring的交易Bean
        String transName = SettleContext.getTransName();
        logger.info("liaccvRegister,取值transName:{}", transName);
        try {
            ILiaccvRegister liaccvRegister = SpringEnvContext.getBean(atpBchCacheService.getSdTransNameForRegister().toLowerCase() + "." + "liaccvSetTransaction");
            liaccvRegister.liaccvSetTransaction(liaccvVo);
        } catch (NoSuchBeanDefinitionException e) {
            throw new CommonServiceException("没有找到交易注册类, {" + transName + "}");
        }
    }

    public void addLiaccvg(LiaccvVo liaccvVo) {
        //! 选取一条保证金，不能选取已选取的
        int num = 0;
        if (liaccvVo.getLiaccvg() != null) {
            num = liaccvVo.getLiaccvg().size();
        }
        logger.info("addLiaccvg,取值num:{}", num);
        int idx = -1;
        for (int line = 0; line < num; line++) {
            LiaccvgVo liaccvgVo = liaccvVo.getLiaccvg().get(line);
            logger.info("addLiaccvg,取值liaccvgVo行数:{},getoldamt:{},getamt:{},getownref:{},getacc:{}", line, liaccvgVo.getOldamt().compareTo(BigDecimal.ZERO), liaccvgVo.getAmt().compareTo(BigDecimal.ZERO), liaccvgVo.getOwnref(), liaccvgVo.getAcc());
            if (liaccvgVo.getOldamt().compareTo(BigDecimal.ZERO) == 0
                    && liaccvgVo.getAmt().compareTo(BigDecimal.ZERO) == 0
                    && StringUtils.isEmpty(liaccvgVo.getOwnref())
                    && StringUtils.isEmpty(liaccvgVo.getAcc())) {
                idx = line;
                break;
            }
        }
        if (idx == -1) {
            LiaccvgVo liaccvgVo = new LiaccvgVo();
            liaccvVo.getLiaccvg().add(liaccvgVo);
            idx = liaccvVo.getLiaccvg().size() - 1;
        }
        FcdVo fcdVo = liaccvVo.getFcdVo();
        logger.info("addLiaccvg,fcdVo.getInr:{}", fcdVo.getInr());
        if (StringUtils.isNotEmpty(fcdVo.getInr())) {
            Fcd fcd = DtoMapper.INSTANCE.transfer(fcdVo);
            //锁住该条fcd数据
            fcdMapper.lockFcd(fcd.getInr());
            //更新fcd数据
            fcd.setUseflg("U");
            logger.info("addLiaccvg,liaccvVo.getRec().getOwnref():{}", liaccvVo.getRec().getOwnref());
            fcd.setRegref(liaccvVo.getRec().getOwnref());
            int row = fcdMapper.updateFcdUseflgAndRegref(fcd.getUseflg(), fcd.getRegref(), fcd.getInr(), "N");
            if (row < 1) {
                throw new CommonServiceException("该笔保证金已经被使用了，请重新选一条数据");
            }
            //查找cbb数据
            Date date = Dates.add(Utils.getMaxDate(), -1);
            Cbb cbb = new Cbb();
            cbsmodService.cbsGetBalance(cbb, "FCD", fcd.getInr(), "OPN", "AMT1", date);
            //更新liaccvg数据
            liaccvVo.getLiaccvg().get(idx).setFcdinr(fcd.getInr());
            liaccvVo.getLiaccvg().get(idx).setCur(cbb.getCur());
            liaccvVo.getLiaccvg().get(idx).setFcdacccur(cbb.getCur());
            liaccvVo.getLiaccvg().get(idx).setAmt(cbb.getAmt());
            liaccvVo.getLiaccvg().get(idx).setFcdavbamt(cbb.getAmt());
            liaccvVo.getLiaccvg().get(idx).setFcdaccamt(new BigDecimal("0"));
            liaccvVo.getLiaccvg().get(idx).setAcc(fcd.getExtact() + fcd.getEngact());
            liaccvVo.getLiaccvg().get(idx).setOwnref(fcd.getOwnref());
            liaccvVo.getLiaccvg().get(idx).setConcur(liaccvVo.getConcur());
            liaccvVo.getLiaccvg().get(idx).setRole(liaccvVo.getNewrol());
            liaccvVo.getLiaccvg().get(idx).setCcvid(calculateCcvid(liaccvVo.getLiaccvg(), liaccvVo.getLiaccvg().get(idx).getCur()));
            calcCcdflgbut(liaccvVo.getLiaccvg().get(idx));
            calcRate(liaccvVo, liaccvVo.getLiaccvg().get(idx));
            calcCovAmts(liaccvVo.getLiaccvg().get(idx));
            logger.info("addLiaccvg,liaccvVo.getLiaccvg().get(idx):{}", liaccvVo.getLiaccvg().get(idx).toString());
            calcTotcovamt(liaccvVo);
            calcRelcshpct(liaccvVo);
            liaccvVo.setAddinf(getAddinf(liaccvVo));
        }
    }

    /**
     * @Default(target="rat",order=1500)
     */
    public void calcRate(LiaccvVo liaccvVo, LiaccvgVo liaccvgVo) {
        Spt spt = sptDataComponent.loadSpt(null);
        String frm = SettleContext.getTransName();
        if (MdaUtils.compareTo(liaccvgVo.getConcur(), liaccvgVo.getCur()) != 0) {
            /**
             if not IsModified( RAT ) and not SptIsAnyLoaded then
             **/
            //if (!liaccvgVo.isModified("rat")) { 20240719czs 实时获取最新牌价
                BigDecimal rate = BigDecimal.ZERO;
                BigDecimal sqrRat = BigDecimal.ZERO;
                BigDecimal midRat = BigDecimal.ZERO;
                if (frm.startsWith("JS") || frm.startsWith("WI")) {
                    Argument<BigDecimal> rateBox = new Argument<BigDecimal>();
                    Argument<BigDecimal> sqrRatBox = new Argument<BigDecimal>();
                    xrtmodService.getrat(liaccvgVo.getConcur(), liaccvgVo.getCur(), "M", Dates.dateAddW(Dates.today(), -1, xrtmodService.calendar()), rateBox, sqrRatBox);
                    rate = rateBox.value;
                    sqrRat = sqrRatBox.value;
                    liaccvgVo.setRat(rate);
                } else {
                    Argument<BigDecimal> rateBox1 = new Argument<BigDecimal>("", rate);
                    Argument<BigDecimal> sqrRatBox1 = new Argument<BigDecimal>("", sqrRat);
                    xrtmodService.getrat(liaccvgVo.getConcur(), liaccvgVo.getCur(), "S", Dates.today(), rateBox1, sqrRatBox1);

                    rate = rateBox1.value;
                    sqrRat = sqrRatBox1.value;

                    Argument<BigDecimal> midRatBox = new Argument<BigDecimal>();
                    Argument<BigDecimal> sqrRatBox2 = new Argument<BigDecimal>("", sqrRat);
                    xrtmodService.getrat(liaccvgVo.getConcur(), liaccvgVo.getCur(), "M", Dates.today(), midRatBox, sqrRatBox2);

                    midRat = midRatBox.value;
                    sqrRat = sqrRatBox2.value;

                    //从PTY表取优惠，不知道为什么
                    Argument<BigDecimal> rateBox2 = new Argument<BigDecimal>("", rate);
                    favoriteRate(liaccvVo, liaccvgVo, midRat, rateBox2);

                    rate = rateBox2.value;
                    /**
                     FavoriteRatePTYRAT( $MidRat, $Rate )
                     **/
                    liaccvgVo.setRat(rate);
                }
            //}
        } else {
            liaccvgVo.setRat(BigDecimal.ONE);
        }
    }

    /**
     * @param liaccvgVo
     * @Default(target="ccdflg",order=1000)
     */
    private void calcCcdflgbut(LiaccvgVo liaccvgVo) {
        //!定期保证金接口标志
        String frmnam = SettleContext.getTransName();
        /**
         if $frmnam == "LITENG" or $frmnam == "GITENG" or $frmnam == "DITENG" then
         **/
        if (Strings.pos("-LITENG-GITENG-NITENG-DITENG-WITENG-JSTENG-", frmnam) > 0) {
            if (!MdaUtils.isEmpty(liaccvgVo.getAcc())) {
                String dh = Strings.mid(liaccvgVo.getAcc(), 7, 4);
                if (MdaUtils.compareTo(dh, "2149") == 0) {  //2149的账户不可勾选Flg
                    //Systems.resetEnabled(this,"ccdflg");
                    liaccvgVo.setCcdflgbut("N");
                } else {
                    if (!MdaUtils.isEmpty(liaccvgVo.getOldamt())) {
                       /* if( MdaUtils.compareTo(this.getCcdflg(),"X") == 0 ) {
                            //当勾选Flg时，Amount不可以手输
                            Systems.setEnabled(this,"ccdflg");
                            Systems.resetEnabled(this,"amt");
                        } else {*/
                        if (!MdaUtils.isEmpty(liaccvgVo.getAmt()) && "".equals(liaccvgVo.getCcdflg())) {
                            //当Amoun有值时，Flg栏位不可勾选
                            //Systems.resetEnabled(this,"ccdflg");
                            liaccvgVo.setCcdflgbut("N");
                            //Systems.setEnabled(this,"amt");
                        } else {
                            //Systems.setEnabled(this,"ccdflg");
                            liaccvgVo.setCcdflgbut("Y");
                            //Systems.setEnabled(this,"amt");
                        }
                        /*}*/
                    } else {
                        //当Old Amount为0时，始终不能勾选Flg
                        //当Old Amount金额为0时，Amount栏位是否可手动输入内容分为两种情况：
                        //1. 手动新增的保证金：Enable(AMT)
                        //2. 定期保证金做部分提支或存款销户带出来的对应的活期保证金：Disable(AMT )
                        /*Systems.resetEnabled(this,"ccdflg");
                        Systems.setEnabled(this,"amt");
                        if( MdaUtils.compareTo(this.getBflg(),"Y") == 0 )
                        {  //BFLG = "Y"表示此记录为定期对应的活期保证金账户
                            Systems.resetEnabled(this,"amt");
                            Systems.resetEnabled(this,"acc");
                        }*/

                    }
                }
            } else {
                //Systems.resetEnabled(this,"ccdflg");
                liaccvgVo.setCcdflgbut("N");
            }
        } else {
            /**
             if $frmnam == "LITENC" or $frmnam == "GITENC" or $frmnam == "DITENC" then
             //如果通过闭卷业务进入此交易设置可勾选，amount不可修改
             if not IsEmpty( \\LIAALL\\LIACCV\\CLOSESTA ) then
             if not IsEmpty( ACC ) then
             Enable( CCDFLG )
             else
             Disable( CCDFLG )
             endif
             Disable( AMT )
             endif
             else
             **/
            //Systems.resetEnabled(this,"ccdflg");
            liaccvgVo.setCcdflgbut("N");
        }
    }

    /**
     * source:liaccvg.0039.script
     */
    public void favoriteRate(LiaccvVo liaccvVo, LiaccvgVo liaccvgVo, BigDecimal midRat, Argument<BigDecimal> rate) {
        String transName = SettleContext.getTransName();
        PtsptaVo ptsptaVo = ptsptaToolComponent.getMainPtspta(transName, liaccvVo.getRec(), liaccvVo.getPtsList());
        if (ptsptaVo != null) {
            Pty pty = ptyCacheService.getPtyById(ptsptaVo.getPtyinr());
            if (pty != null) {
                String buyTyp = pty.getBuytyp();
                BigDecimal buyRat = pty.getBuyrat();
                String selTyp = pty.getSeltyp();
                BigDecimal selRat = pty.getSelrat();
                if (MdaUtils.compareTo(liaccvgVo.getConcur(), "CNY") == 0 && MdaUtils.compareTo(liaccvgVo.getCur(), "CNY") != 0) {
                    // 买价B
                    if (MdaUtils.compareTo(buyTyp, "1") == 0) {
                        //日元从小数点后6位开始优惠
                        if (MdaUtils.compareTo(liaccvgVo.getCur(), "JPY") == 0) {
                            rate.value = Decimals.add(rate.value, Decimals.div(buyRat, 1000000));
                        } else {
                            rate.value = Decimals.add(rate.value, Decimals.div(buyRat, 10000));
                        }
                    }
                    if (MdaUtils.compareTo(buyTyp, "2") == 0) {
                        rate.value = Decimals.add(rate.value, Decimals.div(Decimals.mul((Decimals.sub(midRat, rate.value)), buyRat), 100));
                    }
                } else {
                    if (MdaUtils.compareTo(liaccvgVo.getConcur(), "CNY") != 0 && MdaUtils.compareTo(liaccvgVo.getCur(), "CNY") == 0) {
                        // 卖价S
                        if (MdaUtils.compareTo(selTyp, "1") == 0) {
                            //日元从小数点后6位开始优惠
                            if (MdaUtils.compareTo(liaccvgVo.getConcur(), "JPY") == 0) {
                                rate.value = Decimals.sub(rate.value, Decimals.div(selRat, 1000000));
                            } else {
                                rate.value = Decimals.sub(rate.value, Decimals.div(selRat, 10000));
                            }
                        }
                        if (MdaUtils.compareTo(selTyp, "2") == 0) {
                            rate.value = Decimals.sub(rate.value, Decimals.div(Decimals.mul((Decimals.sub(rate.value, midRat)), selRat), 100));
                        }
                    }
                }
            }
        }
    }

    public void deleteLiaccvg(LiaccvVo liaccvVo) {
        FcdVo fcdVo = liaccvVo.getFcdVo();
        logger.info("deleteLiaccvg,fcdVo.getInr():{}", fcdVo.getInr());
        if (StringUtils.isNotEmpty(fcdVo.getInr())) {
            Fcd fcd = DtoMapper.INSTANCE.transfer(fcdVo);
            fcd = fcdMapper.selectByPrimaryKey(fcd);
            fcd.setUseflg("N");
            fcd.setPnttyp("");
            fcd.setPntinr("");
            fcd.setRegref("");
            logger.info("addLiaccvg,fcd.tostring:{}", fcd.toString());
            fcdMapper.updateFcdUseflgAndRegref(fcd.getUseflg(), fcd.getRegref(), fcd.getInr(), "U");
            liaccvVo.getLiaccvg().removeIf(liaccvgVo -> fcdVo.getInr().equals(liaccvgVo.getFcdinr()));
            //重新计算金额和实收比例
            calcTotcovamt(liaccvVo);
            calcRelcshpct(liaccvVo);
            liaccvVo.setAddinf(getAddinf(liaccvVo));
        }
    }

    //@Default(target="totcovamt",order=1000)
    public void calcTotcovamt(LiaccvVo liaccvVo) {
        BigDecimal amt = new BigDecimal("0");
        logger.info("calcTotcovamt,liaccvVo.getLiaccvg().size():{}", liaccvVo.getLiaccvg().size());
        for (int i = 0; i < liaccvVo.getLiaccvg().size(); i++) {
            amt = Decimals.add(amt, liaccvVo.getLiaccvg().get(i).getCovamt());
            logger.info("calcTotcovamt,循环i:{},amt:{}", i, amt);
        }
        liaccvVo.setTotcovamt(amt);
    }

    /**
     * 计算保证金失守比例
     *
     * @param liaccvVo
     */
    public void calcRelcshpct(LiaccvVo liaccvVo) {
        //>>>zt>>>>>>>>>>>>>>>>>>>>>
        //>>>计算保证金实收比例，将所有保证金相加除以MAX金额
        //>>>end>>>>>>>>>>>>>>>>>>>>
        BigDecimal amount = liaccvVo.getTotcovamt();
        BigDecimal maxamt = Decimals.add(liaccvVo.getOldamt(), liaccvVo.getChgamt());
        logger.info("calcRelcshpct,amount:{},maxamt:{}", amount, maxamt);
        if (MdaUtils.compareTo(amount, 0) >= 0 && MdaUtils.compareTo(maxamt, 0) > 0) {
            liaccvVo.setRelcshpct(Decimals.mul(amount.divide(maxamt, 4, BigDecimal.ROUND_HALF_UP), 100));
        } else {
            if (MdaUtils.compareTo(maxamt, 0) == 0) {
                liaccvVo.setRelcshpct(BigDecimal.ZERO);
            }
        }
    }

    /**
     * 附加信息
     *
     * @return
     */
    public String getAddinf(LiaccvVo liaccvVo) {
        String addinf = "";
        int gridcnt = liaccvVo.getLiaccvg().size();
        logger.info("getAddinf,gridcnt:{}", gridcnt);
        LiaccvgVo liaccvgVo = null;
        for (int i = 0; i < gridcnt; i++) {
            liaccvgVo = liaccvVo.getLiaccvg().get(i);
            if ((!MdaUtils.isEmpty(liaccvgVo.getFcdinr()))
                    && (!MdaUtils.isEmpty(liaccvgVo.getAmt()))
                    && (!"N".equals(getFcduseflg()))) {
                addinf += Strings.getText("保证金       $1     $2 $3    ", liaccvgVo.getOwnref(), liaccvgVo.getCur(), Utils.fmtAmount(liaccvgVo.getAmt(), liaccvgVo.getCur()));
                logger.info("getAddinf,i:{},addinf:{}", i, addinf);
                if (i < gridcnt - 1) {
                    addinf += CR;
                }
            }
        }
        return addinf;
    }

    /**
     * source:liaccvg.0024.script
     */
    //@Default(value={"covamt","acccovamt","amt"},order=500)
    public void calcCovAmts(LiaccvgVo liaccvgVo) {
        String frm = SettleContext.getDirectTransName();
        String refcur = "";
        BigDecimal refamt = new BigDecimal("0.00");
        logger.info("calcCovAmts,frm:{},refamt:{}", frm, refamt);
        switch (frm) {
            case "LITCAN":
            case "GITCAN":
            case "NITCAN":
            case "HITCAN":
            case "DITCAN":
                //信用证与保证金撤销交易自动退还保证金
                if (MdaUtils.compareTo(liaccvgVo.getOldamt(), 0) > 0) {
                    if (!liaccvgVo.isModified("amt")) {
                        liaccvgVo.setAmt(liaccvgVo.getOldamt().negate());
                    }
                    if (MdaUtils.isEmpty(liaccvgVo.getRat())) {
                        liaccvgVo.setAcccovamt(xrtmodService.amtConvTypes(liaccvgVo.getCur(), liaccvgVo.getAmt(), "B", liaccvgVo.getConcur(), "S", Dates.today()));
                    } else {
                        Argument<String> refcurBox = new Argument<String>("", refcur);
                        Argument<BigDecimal> refamtBox = new Argument<BigDecimal>("", refamt);
                        liaccvgVo.setAcccovamt(xrtmodService.amtConvRates(liaccvgVo.getAmt(), new BigDecimal(Double.toString(1.00)), liaccvgVo.getRat(), liaccvgVo.getCur(), liaccvgVo.getConcur(), refcurBox, refamtBox));

                        refcur = refcurBox.value;
                        refamt = refamtBox.value;
                    }
                    liaccvgVo.setCovamt(Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()));
                    logger.info("calcCovAmts,Amt:{},Acccovamt:{},refcur:{},refamt:{},Covamt:{}", liaccvgVo.getAmt(), liaccvgVo.getAcccovamt(), refcur, refamt, liaccvgVo.getCovamt());
                }
                break;
            case "BRTSET":
            case "GITSET":
            case "GITPSE":
            case "NITSET":
            case "NITPSE":
            case "BDTSET":
                //    if not IsEmpty( OLDAMT ) and IsEmpty( \\TRNMOD\\ORDMOD\\ORD\\SDHFLG ) then
                if (!MdaUtils.isEmpty(liaccvgVo.getOldamt())) {
                    if (MdaUtils.compareTo(liaccvgVo.getConcur(), liaccvgVo.getCur()) != 0) {
                        if (!MdaUtils.isEmpty(liaccvgVo.getAcccovamt()) && !MdaUtils.isEmpty(liaccvgVo.getRat())) {
                            Argument<String> refcurBox1 = new Argument<String>("", refcur);
                            Argument<BigDecimal> refamtBox1 = new Argument<BigDecimal>("", refamt);
                            liaccvgVo.setAmt(xrtmodService.amtConvRates(liaccvgVo.getAcccovamt(), liaccvgVo.getRat(), new BigDecimal(Double.toString(1.00)), liaccvgVo.getConcur(), liaccvgVo.getCur(), refcurBox1, refamtBox1));

                            refcur = refcurBox1.value;
                            refamt = refamtBox1.value;

                        } else {
                            if (MdaUtils.compareTo(liaccvgVo.getAcccovamt(), 0) == 0) {
                                liaccvgVo.setAmt(new BigDecimal("0"));
                            }
                        }
                        Argument<String> refcurBox2 = new Argument<String>("", refcur);
                        Argument<BigDecimal> refamtBox2 = new Argument<BigDecimal>("", refamt);
                        liaccvgVo.setCovamt(xrtmodService.amtConvRates(Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()), new BigDecimal(Double.toString(1.00)), liaccvgVo.getRat(), liaccvgVo.getCur(), liaccvgVo.getConcur(), refcurBox2, refamtBox2));

                        refcur = refcurBox2.value;
                        refamt = refamtBox2.value;

                    } else {
                        liaccvgVo.setAmt(liaccvgVo.getAcccovamt());
                        liaccvgVo.setCovamt(Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()));
                    }
                }
                logger.info("calcCovAmts,Amt:{},Acccovamt:{},refcur:{},refamt:{},Covamt:{}", liaccvgVo.getAmt(), liaccvgVo.getAcccovamt(), refcur, refamt, liaccvgVo.getCovamt());
                break;
            default:
                if (MdaUtils.compareTo(liaccvgVo.getConcur(), liaccvgVo.getCur()) != 0) {
                    /**
                     if not IsModified( RAT ) then
                     **/
                    if (MdaUtils.isEmpty(liaccvgVo.getRat())) {
                        if (MdaUtils.compareTo(Strings.mid(frm, 1, 2), "JS") == 0 || MdaUtils.compareTo(Strings.mid(frm, 1, 2), "WI") == 0) {
                            liaccvgVo.setAcccovamt(xrtmodService.amtConvTypes(liaccvgVo.getCur(), liaccvgVo.getAmt(), "B", liaccvgVo.getConcur(), "S", Dates.dateAddW(Dates.today(), -1, xrtmodService.calendar())));
                            liaccvgVo.setCovamt(xrtmodService.amtConvTypes(liaccvgVo.getCur(), Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()), "B", liaccvgVo.getConcur(), "S", Dates.dateAddW(Dates.today(), -1, xrtmodService.calendar())));
                        } else {
                            liaccvgVo.setAcccovamt(xrtmodService.amtConvTypes(liaccvgVo.getCur(), liaccvgVo.getAmt(), "B", liaccvgVo.getConcur(), "S", Dates.today()));
                            liaccvgVo.setCovamt(xrtmodService.amtConvTypes(liaccvgVo.getCur(), Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()), "B", liaccvgVo.getConcur(), "S", Dates.today()));
                        }
                        refcur = xrtmodService.sysiso();
                        refamt = new BigDecimal("0.00");
                        //      endif
                        logger.info("calcCovAmts,Amt:{},Acccovamt:{},refcur:{},refamt:{},Covamt:{}", liaccvgVo.getAmt(), liaccvgVo.getAcccovamt(), refcur, refamt, liaccvgVo.getCovamt());
                    } else {
                        Argument<String> refcurBox3 = new Argument<String>("", refcur);
                        Argument<BigDecimal> refamtBox3 = new Argument<BigDecimal>("", refamt);
                        liaccvgVo.setAcccovamt(xrtmodService.amtConvRates(liaccvgVo.getAmt(), new BigDecimal(Double.toString(1.00)), liaccvgVo.getRat(), liaccvgVo.getCur(), liaccvgVo.getConcur(), refcurBox3, refamtBox3));

                        refcur = refcurBox3.value;
                        refamt = refamtBox3.value;

                        Argument<String> refcurBox4 = new Argument<String>("", refcur);
                        Argument<BigDecimal> refamtBox4 = new Argument<BigDecimal>("", refamt);
                        liaccvgVo.setCovamt(xrtmodService.amtConvRates(Decimals.add(liaccvgVo.getAmt(), liaccvgVo.getOldamt()), new BigDecimal(Double.toString(1.00)), liaccvgVo.getRat(), liaccvgVo.getCur(), liaccvgVo.getConcur(), refcurBox4, refamtBox4));

                        refcur = refcurBox4.value;
                        refamt = refamtBox4.value;

                    }
                } else {
                    liaccvgVo.setCovamt(Decimals.add(liaccvgVo.getOldamt(), liaccvgVo.getAmt()));
                    liaccvgVo.setAcccovamt(liaccvgVo.getAmt());
                }
                logger.info("calcCovAmts,Amt:{},Acccovamt:{},refcur:{},refamt:{},Covamt:{}", liaccvgVo.getAmt(), liaccvgVo.getAcccovamt(), refcur, refamt, liaccvgVo.getCovamt());
        }
    }

    //@Init(order=500)
    public String getFcduseflg() {
        return "U";
    }

    public List<FcdVo> getFcdList(String transName, LiaccvVo liaccvVo) {
        logger.info("getFcdList,transName:{},getRec:{},getPtsList:{}", transName, liaccvVo.getRec(), liaccvVo.getPtsList());
        if (StringUtils.isEmpty(transName)) {
            return null;
        }
        transName = transName.toUpperCase();
        PtsptaVo ptsptaVo = ptsptaToolComponent.getMainPtspta(transName, liaccvVo.getRec(), liaccvVo.getPtsList());
        List<FcdVo> list = new ArrayList<>();
        if (ptsptaVo != null) {
            String ptyinr = ptsptaVo.getPtyinr();
            if (StringUtils.isEmpty(ptyinr)) {
                ptyinr = ptsptaVo.getPts().getPtyinr();
            }
            String bussec = transName.substring(0, 2);
            List<Fcd> fcds = fcdMapper.getFcdByPtyinr(ptyinr, bussec);
            fcds.forEach(fcd -> list.add(DtoMapper.INSTANCE.transfer(fcd)));
        }
        logger.info("getFcdList,list:{}", list.toString());
        return list;
    }

    /**
     * source:liaccv.0027.script
     */
    public void fcdSav3000(String ordInr, LiaccvVo liaccvVo) {
        //将业务中选取的保证金与ord关联起来。
        //ordinr -- 传入的ord表的inr号
        //更新fcd表中pnttyp 与 pntinr
        //适用于opn,ame,rop交易
        String name = SettleContext.getTransName();
        /**
         if $name == "LITOPN" or $name == "GITOPN" or $name == "LITAME" or $name == "GITAME" or $name == "LITROP" or $name == "GITROP" or $name == "DITOPN" or $name == "DITAME" then
         **/
        if (MdaUtils.compareTo(name, "LITOPN") == 0
                || MdaUtils.compareTo(name, "GITOPN") == 0
                || MdaUtils.compareTo(name, "NITOPN") == 0
                || MdaUtils.compareTo(name, "HITOPN") == 0
                || MdaUtils.compareTo(name, "LITAME") == 0
                || MdaUtils.compareTo(name, "GITAME") == 0
                || MdaUtils.compareTo(name, "NITAME") == 0
                || MdaUtils.compareTo(name, "HITAME") == 0
                || MdaUtils.compareTo(name, "LITROP") == 0
                || MdaUtils.compareTo(name, "GITROP") == 0
                || MdaUtils.compareTo(name, "DITOPN") == 0
                || MdaUtils.compareTo(name, "DITAME") == 0
                || MdaUtils.compareTo(name, "GITODZ") == 0) {
            List<LiaccvgVo> liaccvgs = liaccvVo.getLiaccvg();
            logger.info("fcdSav3000,liaccvgs条数:{}", liaccvgs.size());
            for (int idx = 0; idx < liaccvgs.size(); idx++) {
                LiaccvgVo liaccvgVo = liaccvgs.get(idx);
                logger.info("fcdSav3000,lliaccvgVo.getownref:{},lliaccvgVo:{}", liaccvgVo.getOwnref(), liaccvgVo.toString());
                if (StringUtils.isNotEmpty(liaccvgVo.getOwnref())) {
                    fcdMapper.updateFcdPnttypAndinrByOwnref("ORD", ordInr, liaccvgVo.getOwnref());
                }
            }
        }

    }

    /**
     * 在原td逻辑中，表外和保证金是没有分离的
     * 由于在最新的组件化里面将保证金和表外分离，所以注册，getold，试算都要分开
     * 因此getold逻辑参考表外的结构写的，只是getOldForContract实现不一样
     *
     * @param liaccvVo
     */
    public void getold(LiaccvVo liaccvVo) {
        // read old data for main contract
        getOldForContract(liaccvVo, SimpleModuleVo.buildModule(liaccvVo.getRec()));
        // read old data for additional contracts 交易注册的时候会注入 liaallSetAdditionalContract
        List<SimpleModuleVo> simpleModuleList = Utils.toListObject(SimpleModuleVo.class, liaallService.liaallParGet("ADDMODULE", "ALL"));
        if (simpleModuleList != null && simpleModuleList.size() > 0) {
            simpleModuleList.forEach(simpleModuleVo -> getOldForContract(liaccvVo, simpleModuleVo));
        }
    }

    public void getOldForContract(LiaccvVo liaccvVo, SimpleModuleVo simpleModuleVo) {
        String objTyp = simpleModuleVo.getObjtyp();
        if (noGetOldFlag(objTyp)) {
            return;
        }
        String objInr = simpleModuleVo.getObjinr();
        logger.info("getOldForContract,objTyp:{},objInr:{}", objTyp, objInr);
        //! checks, if there are old cash cover balances for module mod.
        Date date = Dates.add(Utils.getMaxDate(), -1);
        logger.info("getOldForContract,date:{}", date);
        Cbb cbb = new Cbb();
        cbsmodService.cbsGetBalance(cbb, objTyp, objInr, "MAXSUM", "CCVAMT", date);
        /**
         //老吴说不要此控制
         if WRKCBB\\AMT <> 0 then
         **/
        // set amount and contract
        liaccvVo.setOldamt(cbb.getAmt());
        liaccvVo.setOldcur(cbb.getCur());
        liaccvVo.setObjmodpath(Utils.toJson(SimpleModuleVo.buildModule(objInr, objTyp)));
        logger.info("getOldForContract,cbb.getAmt:{},cbb.getCur:{},SimpleModule:{}", cbb.getAmt(), cbb.getCur(), Utils.toJson(simpleModuleVo));
        /**
         $LSTCBENAM = GetTextOfInrTable( "CBE", WRKCBB\\CBEINR, "NAM" )
         CSHPCT = Val( Mid( $LSTCBENAM, Pos( $LSTCBENAM, TAB ) + 1, Len( $LSTCBENAM ) - Pos( $LSTCBENAM, TAB ) ) )
         **/
        //保证金应收比例从业务表中取值
        Spt spt = sptDataComponent.loadSpt(null);
        if (spt == null || !sysmodService.sptIsAnyLoaded(spt.getSta())) {
            if (liaccvVo.getCshpct().compareTo(BigDecimal.ZERO) == 0) {
                BigDecimal cshpct = dyncDaoService.dyncReadFieldByInr(objTyp.toUpperCase(), objInr, "cshpct");
                if (cshpct != null) {
                    liaccvVo.setCshpct(cshpct);
                }
            }
            logger.info("getOldForContract,cshpct:{}", liaccvVo.getCshpct());
            //增加CLOSESTA字段：空表示不是闭卷，Y表示已经闭卷
            //CLOSESTA字段主要用于闭卷后的定期保证金解冻使用
            Date clsdat = dyncDaoService.dyncReadFieldByInr(objTyp.toUpperCase(), objInr, "clsdat");
            logger.info("getOldForContract,clsdat:{}", clsdat);
            if (clsdat != null) {
                liaccvVo.setClosesta("Y");
            }
        }
        cbsmodService.cbsGetBalance(cbb, objTyp, objInr, "MAXSUM", "CCVRESAMT", date);
        liaccvVo.setOldresamt(cbb.getAmt());
        logger.info("getOldForContract闭卷后定期保证金处理,Oldresamt:{}", cbb.getAmt());
        getOldCovers(liaccvVo, objTyp, objInr, false);
        //闭卷后做定期保证金解冻
        if ("Y".equals(liaccvVo.getClosesta())) {
            //getOldregularcashCovers( mod ); 以下方法替代
            getOldCovers(liaccvVo, objTyp, objInr, true);
        }
    }

    /**
     * source:liaccv.0006.script
     */
    public void getOldCovers(LiaccvVo liaccvVo, String objTyp, String objInr, boolean closeFlag) {
        //! internal function to read old cover entries for contract mod in LIACCVG
        // get lines with old amount (e.g. when picking up a pending item)
        //colseFlag = true 代表的是原getOldregularcashCovers方法
        //由于闭卷后进入保证金调整交易后保证金界面纪录将不会带出任何纪录，故调整getOldCovers逻辑查询出定期保证金的纪录
        logger.info("getOldCovers由于闭卷后进入保证金调整交易后保证金界面纪录将不会带出任何纪录，故调整getOldCovers逻辑查询出定期保证金的纪录");
        logger.info("getOldCovers,参数objTyp:{},objInr:{},closeFlag:{}.", objTyp, objInr, closeFlag);
        Spt spt = sptDataComponent.loadSpt(null);
        logger.info("getOldCovers,spt:{}", spt);
        // get stored EXTIDs
        Date date = Dates.add(Utils.getMaxDate(), -1);
        List<String> extids = cbsget.cbsGetUnbalancedExtIds(objTyp, objInr, "CCVSUM");
        logger.info("getOldCovers,date:{},extids:{}.", date, extids.toString());
        if (closeFlag) {
            List<SimpleModuleVo> simpleModuleList = Utils.toListObject(SimpleModuleVo.class, liaallService.liaallParGet("ADDMODULE", "ALL"));
            logger.info("getOldCovers,simpleModuleList:{}.", simpleModuleList);
            if (simpleModuleList != null && simpleModuleList.size() > 0) {
                simpleModuleList.forEach(simpleModuleVo -> {
                    //如果不是同一个模型(inr和typ都一样)
                    if (!objInr.equals(simpleModuleVo.getObjinr()) || !objTyp.equals(simpleModuleVo.getObjtyp())) {
                        extids.addAll(cbsget.cbsGetUnbalancedExtIds(simpleModuleVo.getObjtyp(), simpleModuleVo.getObjinr(), "CCVSUM"));
                    }
                });
            }
        }
        extids.forEach(extid -> {
            Cbb cbb = new Cbb();
            cbsmodService.cbsGetBalance(cbb, objTyp, objInr, "CCVSUM", extid, date);
            logger.info("getOldCovers,cbb:{}.", cbb.toString());
            if (cbb.getAmt().compareTo(BigDecimal.ZERO) != 0) {
                int use = -1;
                for (int i = 0; i < liaccvVo.getLiaccvg().size(); i++) {
                    String liaccvgExtid = liaccvVo.getLiaccvg().get(i).getRole() + "/" + liaccvVo.getLiaccvg().get(i).getCcvid();
                    boolean continueFlag = true;
                    if (closeFlag) {
                        //只显示定期保证金的纪录
                        Cbe cbe = new Cbe();
                        cbe.setInr(cbb.getCbeinr());
                        cbe = cbeMapper.selectByPrimaryKey(cbe);
                        logger.info("getOldCovers,cbe:{}.", cbe);
                        String cbeacc = cbe.getAcc();
                        String dflg = "";
                        if (Strings.len(cbeacc) == 17) {
                            dflg = Strings.mid(cbeacc, 7, 2);
                        }
                        if (Strings.len(cbeacc) == 21) {
                            dflg = Strings.mid(cbeacc, 11, 2);
                        }
                        if (MdaUtils.compareTo(Strings.mid(cbeacc, 1, 3), "ZMQ") == 0 || MdaUtils.compareTo(Strings.mid(cbeacc, 1, 3), "NRA") == 0) {
                            dflg = Strings.mid(cbeacc, 10, 2);
                        }
                        if (!"81".equals(dflg)) {
                            continueFlag = false;
                        }
                    }
                    //如果闭卷的时候dflg不等于81 按照原逻辑就不会走一下的代码
                    if (!continueFlag) continue;
                    if (extid.equals(liaccvgExtid)) {
                        use = i;
                    } else {
                        if (liaccvVo.getLiaccvg().get(i).getOldamt().compareTo(BigDecimal.ZERO) == 0
                                && liaccvVo.getLiaccvg().get(i).getAmt().compareTo(BigDecimal.ZERO) == 0) {
                            //复用金额都为0的liaccvg条目
                            use = i;
                        }
                    }
                }
                if (use == -1) {
                    //表示没有找到 则需要新增一条liaccvg记录
                    LiaccvgVo liaccvgVo = new LiaccvgVo();
                    liaccvVo.getLiaccvg().add(liaccvgVo);
                    //use等于新增的一笔数据下标
                    use = liaccvVo.getLiaccvg().size() - 1;
                }
                // set old info in that line
                logger.info("getOldCovers,use:{},liaccvVo.getLiaccvg().get(use):{}.", use, liaccvVo.getLiaccvg().get(use).toString());
                liaccvVo.getLiaccvg().get(use).setCur(cbb.getCur());
                liaccvVo.getLiaccvg().get(use).setConcur(liaccvVo.getConcur());
                liaccvVo.getLiaccvg().get(use).setOldamt(cbb.getAmt());
                liaccvVo.getLiaccvg().get(use).setCcvid(Strings.mid(extid, 5));
                liaccvVo.getLiaccvg().get(use).setRole(Strings.mid(extid, 1, 3));
                if (MdaUtils.isEmpty(liaccvVo.getNewrol())) {
                    liaccvVo.setNewrol(liaccvVo.getLiaccvg().get(use).getRole());
                }
                liaccvVo.getLiaccvg().get(use).setOldflg("X");
                if (spt == null || !sysmodService.sptIsAnyLoaded(spt.getSta())) {
                    //---------------YSP------------
                    BigDecimal rat = BigDecimal.ZERO;
                    if (MdaUtils.compareTo(Strings.mid(SettleContext.getUserSession().getAtp().getCod(), 1, 2), "JS") == 0
                            || MdaUtils.compareTo(Strings.mid(SettleContext.getUserSession().getAtp().getCod(), 1, 2), "WI") == 0) {
                        Argument<BigDecimal> ratBox = new Argument<BigDecimal>();
                        liaccvVo.getLiaccvg().get(use).setCovamt(xrtmodService.amtConvTypesWithCrossrate(liaccvVo.getLiaccvg().get(use).getCur(), liaccvVo.getLiaccvg().get(use).getOldamt(), "B", liaccvVo.getOldcur(), "S", Dates.dateAddW(Dates.today(), -1, xrtmodService.calendar()), ratBox));
                        rat = ratBox.value;
                    } else {
                        Argument<BigDecimal> ratBox1 = new Argument<BigDecimal>("", rat);
                        liaccvVo.getLiaccvg().get(use).setCovamt(xrtmodService.amtConvTypesWithCrossrate(liaccvVo.getLiaccvg().get(use).getCur(), liaccvVo.getLiaccvg().get(use).getOldamt(), "B", liaccvVo.getOldcur(), "S", Dates.today(), ratBox1));
                        rat = ratBox1.value;
                    }
                    liaccvVo.getLiaccvg().get(use).setRat(rat);
                }
                // get information about forward contract
                Cbe cbe = new Cbe();
                cbe.setInr(cbb.getCbeinr());
                cbe = cbeMapper.selectByPrimaryKey(cbe);
                logger.info("getOldCovers,cbe:{}.", cbe);
                if (cbe != null) {
                    liaccvVo.getLiaccvg().get(use).setAcc(cbe.getAcc());
                    String lstcbenam = cbe.getNam();
                    if (Strings.len(lstcbenam) > 20
                            && MdaUtils.compareTo(Strings.mid(lstcbenam, Strings.len(lstcbenam) - 1, 2), " )") == 0) {
                        String fchownref = Strings.mid(lstcbenam, Strings.len(lstcbenam) - 17, 16);
                        int pos = Strings.pos(fchownref, " ");
                        if (pos > 0) {
                            fchownref = Strings.mid(fchownref, pos + 1);
                        }
                        liaccvVo.getLiaccvg().get(use).setOwnref(fchownref);
                        Fcd fcd = fcdMapper.getFcdByOwnref(fchownref);
                        if (fcd != null) {
                            FcdCbbAmtInfoVo fcdCbbAmtInfoVo = sesmodGetAvbFCD(fcd.getInr(), liaccvVo.getLiaccvg().get(use).getCur());
                            BigDecimal opnAmt = Utils.getFieldValue(fcdCbbAmtInfoVo, "OPNAMT");
                            if (opnAmt == null || opnAmt.compareTo(BigDecimal.ZERO) == 0) {
                                liaccvVo.getLiaccvg().get(use).setOldfcdinr(NULLSTR);
                            } else {
                                liaccvVo.getLiaccvg().get(use).setFcdavbamt(Utils.getFieldValue(fcdCbbAmtInfoVo, "AVBAMT"));
                                //ctx.absGet(Trnmod.class).troLockContractForCBSOnly ( this.getFcdgrp());
                            }
                        }
                    }
                }
                //计算ccdflg
                calcCcdflgbut(liaccvVo.getLiaccvg().get(use));
            }
        });
    }

    /**
     * source:liaccv.0010.script
     */
    public <T> T getfcdoldamt(String amttyp, String fcdinr, String cur) {
        //! gets amount of forward contract (open-held amounts)
        //! Available types (AMTTYP) are:
        //! OPNAMT open amount
        //! HLDAMT amount held for cash cover (incl. this one)
        //! XRFAMT amount held for cash cover ind HOLD currency
        //! AVBAMT (available amount (difference of OPNAMT and HLDAMT))
        logger.info("getfcdoldamt,参数amttyp:{},fcdinr:{},cur:{}", amttyp, fcdinr, cur);
        FcdCbbAmtInfoVo fcdCbbAmtInfoVo = sesmodGetAvbFCD(fcdinr, cur);
        return Utils.getFieldValue(fcdCbbAmtInfoVo, amttyp);
    }

    /**
     * source:liaccv.0013.script
     */
    public FcdCbbAmtInfoVo sesmodGetAvbFCD(String fcdinr, String cur) {
        logger.info("sesmodGetAvbFCD,参数fcdinr:{},cur:{}", fcdinr, cur);
        //通过构造对象FcdCbbAmtInfoVo 来替代原来Stream,CacheRead,CacheWrite的逻辑
        FcdCbbAmtInfoVo.FcdCbbAmtInfoVoBuilder builder = FcdCbbAmtInfoVo.builder();
        builder.fcdInr(fcdinr);
        Cbb cbb = new Cbb();
        Fcd fcd = fcdMapper.getFcdByInr(fcdinr);
        Date date = Dates.add(Utils.getMaxDate(), -1);
        cbsmodService.cbsGetBalance(cbb, "FCD", fcdinr, "OPN", "AMT1", date);
        if (cbb.getAmt().compareTo(BigDecimal.ZERO) > 0 && cur.equals(cbb.getCur())) {
            BigDecimal opnAmt = cbb.getAmt();
            builder.opnAmt(opnAmt);
            cbsmodService.cbsGetBalance(cbb, "FCD", fcdinr, "HLD", "AMT1", date);
            if (cbb != null) {
                builder.hldAmt(cbb.getAmt())
                        .xrfAmt(cbb.getXrfamt())
                        .avbAmt(Decimals.sub(opnAmt, cbb.getAmt()))
                        .ownRef(fcd.getOwnref())
                        .dcbRat(fcd.getDcbextrat())
                        .scbRat(fcd.getScbextrat());
            }
            logger.info("sesmodGetAvbFCD,opnAmt:{},cbb.getAmt:{},cbb.getXrfamt:{},Decimals.sub(opnAmt, cbb.getAmt()):{},fcd.getOwnref():{},fcd.getDcbextrat():{},fcd.getScbextrat():{}", opnAmt, cbb.getAmt(), cbb.getXrfamt(), Decimals.sub(opnAmt, cbb.getAmt()), fcd.getOwnref(), fcd.getDcbextrat(), fcd.getScbextrat());
        }
        return builder.build();
    }

    /**
     * source:liaccvg.0016.script
     *
     * @Default(target="acplia.cbe.extid",order=1000) 设置cbe的extid = role + / + cur + index
     */
    private void setAcpliaCbeExtId(LiaccvVo liaccvVo, int index) {
        logger.info("setAcpliaCbeExtId,参数index:{},liaccvVo:{}", index, liaccvVo.toString());
        LiaccvgVo liaccvgVo = liaccvVo.getLiaccvg().get(index);
        liaccvgVo.getAcplia().getCbe().setExtid((StringUtils.isEmpty(liaccvgVo.getRole()) ? "APL" : liaccvgVo.getRole()) + "/" + liaccvgVo.getCcvid());
    }

    /**
     * @Default(target="pctresamt",order=1000)
     */
    public void calcPctresamt(LiaccvVo liaccvVo) {
        String transName = SettleContext.getTransName();
        if (MdaUtils.compareTo(transName, "BRTSET") == 0
                || MdaUtils.compareTo(transName, "GITSET") == 0
                || MdaUtils.compareTo(transName, "GITPSE") == 0
                || MdaUtils.compareTo(transName, "NITSET") == 0
                || MdaUtils.compareTo(transName, "NITPSE") == 0
                || MdaUtils.compareTo(transName, "BDTSET") == 0) {
            liaccvVo.setPctresamt(Numerics.abs(Decimals.div(Decimals.mul(liaccvVo.getCshpct(), liaccvVo.getChgamt()), 100)));
        } else {
            liaccvVo.setPctresamt(new BigDecimal(0));
        }
    }

    /**
     * source:liaccv.0003.script
     *
     * @Default(target="newamt",order=1000)
     */
    public void calcNewamt(LiaccvVo liaccvVo) {
        //! Set New amount to
        //! OLDAMT + CHGAMT if no currency chage take place
        //! if curreny is changed, the change amount is taken
        if (MdaUtils.compareTo(liaccvVo.getOldcur(), liaccvVo.getConcur()) == 0) {
            liaccvVo.setNewamt(Decimals.add(liaccvVo.getOldamt(), liaccvVo.getChgamt()));
        } else {
            liaccvVo.setNewamt(liaccvVo.getChgamt());
        }
    }

    /**
     * 计算mac值
     *
     * @param liaccvVo
     * @return
     */
    private String calcMac(LiaccvVo liaccvVo) {
        IStream stream = new StreamImpl();
        stream.addLine(liaccvVo.getConcur());
        stream.addLine(liaccvVo.getOldredflg());
        stream.addLine(liaccvVo.getRec().getObjinr() + liaccvVo.getRec().getObjtyp());
        if (getLiaallSet().getCancelModule() != null) {
            stream.addLine(Utils.toJson(getLiaallSet().getCancelModule()));
        }
        stream.addLine(liaccvVo.getCbeListJson());
        stream.addLine(liaallService.liaallParGet("CCV", "ROL"));
        stream.addLine(liaallService.liaallParGet("CCV", "AMT"));
        stream.addLine(liaallService.liaallParGet("CCV", "MOD"));
        stream.addLine(liaallService.liaallParGet("CCVRES", "MOD"));
        stream.addLine(liaallService.liaallParGet("CCVRES", "AMT"));
        for (int i = 0; i < liaccvVo.getLiaccvg().size(); i++) {
            LiaccvgVo liaccvgVo = liaccvVo.getLiaccvg().get(i);
            stream.addLine(liaccvgVo.getOwnref() + liaccvgVo.getCur()
                    + MdaUtils.toString(Numerics.round(liaccvgVo.getOldamt(), 2))
                    + MdaUtils.toString(Numerics.round(liaccvgVo.getAmt(), 2))
                    + liaccvgVo.getAcc()
                    + MdaUtils.toString(Numerics.round(liaccvgVo.getRat(), 6))
                    + liaccvgVo.getConcur()
                    + MdaUtils.toString(Numerics.round(liaccvgVo.getCovamt(), 2))
                    + MdaUtils.toString(Numerics.round(liaccvgVo.getAcccovamt(), 2))
            );
        }
        String mac = Systems.macGen(stream, 0);
        return mac;
    }

    /**
     * 某些交易 可以更新保证金应收比例
     * 考虑收单行业务场景
     * @param liaccvVo
     */
    private void updateCshpct(LiaccvVo liaccvVo) {
        String transName = SettleContext.getTransName();
        BizInfoVo rec = liaccvVo.getRec();
        if ("GITENG|GITOPN".indexOf(transName) > -1) {
            Object object = dyncDaoService.dyncReadByInr(Gid.class, rec.getObjinr());
            Utils.setFieldValue(object, "cshpct", liaccvVo.getCshpct());
            dyncDaoService.dyncUpdateByPrimaryKey(object);
        } else if ("NITENG|NITOPN|HITOPN".indexOf(transName) > -1) {
            Object object = dyncDaoService.dyncReadByInr(Nid.class, rec.getObjinr());
            Utils.setFieldValue(object, "cshpct", liaccvVo.getCshpct());
            dyncDaoService.dyncUpdateByPrimaryKey(object);
        } else if ("LITENG".indexOf(transName) > -1) {
            Object object = dyncDaoService.dyncReadByInr(Lid.class, rec.getObjinr());
            Utils.setFieldValue(object, "cshpct", liaccvVo.getCshpct());
            dyncDaoService.dyncUpdateByPrimaryKey(object);
        } else if ("DITENG".indexOf(transName) > -1) {
            Object object = dyncDaoService.dyncReadByInr(Did.class, rec.getObjinr());
            Utils.setFieldValue(object, "cshpct", liaccvVo.getCshpct());
            dyncDaoService.dyncUpdateByPrimaryKey(object);
        } else if ("JSTENG".indexOf(transName) > -1) {
            Object object = dyncDaoService.dyncReadByInr(Jsd.class, rec.getObjinr());
            Utils.setFieldValue(object, "cshpct", liaccvVo.getCshpct());
            dyncDaoService.dyncUpdateByPrimaryKey(object);
        }
    }

    /**
     * 检查保证金是否发生变化
     * @param liaccvVo
     */
    private void checkLiaccvChange(LiaccvVo liaccvVo) {
        logger.info("检查保证金CBE列表是否发生编号");
        String cbeListJson = liaccvVo.getCbeListJson();
        logger.info("原始CBE列表={}",cbeListJson);
        List<SimpleCbeVo> simpleCbeList = new ArrayList<>();
        SimpleModuleVo linkModuleVo = SimpleModuleVo.buildModule(liaccvVo.getRec());
        List<Cbe> cbeList = cbeMapper.getCcvCbeList(linkModuleVo.getObjtyp(), linkModuleVo.getObjinr());
        if (cbeList != null) {
            simpleCbeList.addAll(DtoMapper.INSTANCE.transfer(cbeList));
        }
        List<SimpleModuleVo> simpleModuleList = Utils.toListObject(SimpleModuleVo.class, liaallService.liaallParGet("ADDMODULE", "ALL"));
        if (simpleModuleList != null) {
            simpleModuleList.forEach(simpleModuleVo -> {
                List<Cbe> cbeList1 = cbeMapper.getCcvCbeList(simpleModuleVo.getObjtyp(), simpleModuleVo.getObjinr());
                if (cbeList1 != null) {
                    simpleCbeList.addAll(DtoMapper.INSTANCE.transfer(cbeList1));
                }
            });
        }
        String dbCbeListJson = Utils.toJson(simpleCbeList);
        logger.info("当前CBE列表={}",dbCbeListJson);
        if (!dbCbeListJson.equals(cbeListJson)) {
            logger.info("检查到CBE列表发生变化，需要重新从数据库获取保证金列表");
            liaccvVo.setOldredflg("");
            liaccvVo.getLiaccvg().clear();
            liaccvVo.setCbeListJson(dbCbeListJson);
        }
    }

    /**
     * 1.根据liaccvg中的CCVID(cur+id)，币种分类，计算得到最大id，放入map中
     * 2.传入币种得到最大id
     * 3.返回ccvid = cur + id
     * @param liaccvgs
     * @param cur
     * @return
     */
    private String calculateCcvid(List<LiaccvgVo> liaccvgs, String cur) {
        String ccvid = "";
        if (liaccvgs == null || liaccvgs.size() == 0) {
            ccvid = cur + "0";
            logger.info("币种{}得到的ccvid为{}", cur, ccvid);
            return ccvid;
        }
        Map<String, Integer> maps = new HashMap<>();
        liaccvgs.forEach(liaccvg -> {
            String tempCcvid = liaccvg.getCcvid();
            if (StringUtils.isNotEmpty(tempCcvid) && tempCcvid.length() >= 3) {
                String ccvidCur = tempCcvid.substring(0, 3);
                String ccvidIdx = tempCcvid.substring(3);
                int idx = 0;
                try {
                    if (StringUtils.isNotEmpty(ccvidIdx)) {
                        idx = Integer.parseInt(ccvidIdx);
                    }
                } catch (Exception e) {
                    logger.error("{}中的下标{}不合法，下标当成0处理", tempCcvid, ccvidIdx);
                }
                if (!maps.containsKey(ccvidCur)) {
                    //不包含直接put进去
                    maps.put(ccvidCur, idx);
                } else {
                    //如果当前下标大于maps中的下标，put进去
                    if (idx > maps.get(ccvidCur)) {
                        maps.put(ccvidCur, idx);
                    }
                }
            }
        });
        logger.info("ccvidMaps数据输出{}", Utils.toJson(maps));
        if (!maps.containsKey(cur)) {
            ccvid = cur + "0";
        } else {
            int idx = maps.get(cur) + 1;
            ccvid = cur + idx;
        }
        logger.info("币种{}得到的ccvid为{}", cur, ccvid);
        return ccvid;
    }

    private boolean noGetOldFlag(String objtyp) {
        if ("GCD".equalsIgnoreCase(objtyp)
            || "NCD".equalsIgnoreCase(objtyp)
            || "BDD".equalsIgnoreCase(objtyp)
            || "BRD".equalsIgnoreCase(objtyp)) {
            return true;
        }
        return false;
    }

    public LiaallSet getLiaallSet() {
        return transactionHelpService.getLiaallSet();
    }

}
