package com.brilliance.isc.common.component;

import com.brilliance.isc.bo.Bch;
import com.brilliance.isc.bo.Cbb;
import com.brilliance.isc.bo.Dfd;
import com.brilliance.isc.bo.Dft;
import com.brilliance.isc.bo.model.Dfacbs;
import com.brilliance.isc.bo.model.Dfdgrp;
import com.brilliance.isc.common.cbsmod.service.CbsmodService;
import com.brilliance.isc.common.context.SettleContext;
import com.brilliance.isc.common.counter.service.CounterService;
import com.brilliance.isc.common.exception.CommonServiceException;
import com.brilliance.isc.common.transaction.help.TransactionServiceSet;
import com.brilliance.isc.common.trnmod.service.TrnmodService;
import com.brilliance.isc.common.util.Utils;
import com.brilliance.isc.common.vo.FremsgVo;
import com.brilliance.isc.common.vo.PtsptaVo;
import com.brilliance.isc.mda.dao.DfdMapper;
import com.brilliance.isc.mda.dao.DftMapper;
import com.brilliance.mda.runtime.mda.util.Dates;
import com.brilliance.mda.runtime.mda.util.MdaUtils;
import com.brilliance.mda.runtime.mda.util.Strings;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.lang.reflect.Field;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

@Component
public class DftmodComponent {

    @Autowired
    private CounterService counterService;

    @Autowired
    private TrnmodService trnmodService;

    @Autowired
    private DfdMapper dfdMapper;

    @Autowired
    private DftMapper dftMapper;

    @Autowired
    private CbsmodService cbsmodService;

    @Autowired
    private PtsptaToolComponent ptsptaToolComponent;

    /**
     *   source:dftmod.0000.script
     */
    public String getref(String ownref, String trntyp) {
        Bch wrkbch = SettleContext.getUserSession().getWrkbch();
        if(MdaUtils.isEmpty(ownref)) {
            ownref = generateDefaultOwnref("DF");
            ownref = Strings.mid(ownref, 1, 12) + wrkbch.getBchflg();
        }
        //不同业务品种下的代付通过最后一位字母区分
        //  L 进口信用证、C进口代收、T汇出汇款、D国内证买方、J国内证卖方
        if( Strings.len(Strings.trim(ownref)) >= 14 ) {
            switch(trntyp) {
                case "BR":
                    ownref = Strings.mid(ownref, 1, 14) + "L";
                    break;
                case "BF":
                    ownref = Strings.mid(ownref, 1, 14) + "J";
                    break;
                case "BC":
                    ownref = Strings.mid(ownref, 1, 14) + "C";
                    break;
                case "CP":
                    ownref = Strings.mid(ownref, 1, 14) + "T";
                    break;
                case "BD":
                    ownref = Strings.mid(ownref, 1, 14) + "D";
                    break;
                default:
                    ownref = Strings.mid(ownref, 1, 14);
            }
        }
        return ownref;
    }

    private String generateDefaultOwnref(String trn) {
        StringBuilder ownRefBufferBuilder = new StringBuilder();
        String branch = getBranchRef();
        // 交易代码 比如 TR，
        ownRefBufferBuilder.append(trn);

        // 4位分行编码
        ownRefBufferBuilder.append(branch);

        // 2位年份
        ownRefBufferBuilder.append(Strings.mid(MdaUtils.toString(Dates.getYear(Dates.today()), 4), 3, 2));

        // 4位流水号
        ownRefBufferBuilder.append(MdaUtils.toString(counterService.dbCounter(trn + branch), -4));

        return ownRefBufferBuilder.toString();
    }

    /**
     * 获得机构所属的分行编号
     * 若分行编号不为空，则直接返回，否则返回机构编号.
     *
     * @param
     * @return
     */
    private String getBranchRef() {
        Bch bch = SettleContext.getUserSession().getBch();
        if (bch != null) {
            return bch.getBranch();
        }
        return "";
    }

    /**
     *   source:dftmod.0003.script
     */
    public void sav(Dfdgrp dfdgrp) {
        // saves contract including texts. CBS resp. of transaction
        if(MdaUtils.isEmpty(dfdgrp.getRec().getCredat())) {
            dfdgrp.getRec().setCredat( Dates.today());
        }
        trnmodService.trnStoreContract(dfdgrp);
    }

    public Dfdgrp getDfdgrpByInr(String inr) {
        Dfdgrp dfdgrp = new Dfdgrp();
        dfdgrp.reset();
        //找LID的数据
        Dfd dfd = dfdgrp.getRec();
        dfd.setInr(inr);
        dfd = dfdMapper.selectByPrimaryKey(dfd);
        if (dfd == null) {
            throw new CommonServiceException("找不到DFD{" + inr + "}数据!");
        }
        dfdgrp.setRec(dfd);
        //找TRT的数据
        Dft dft = dfdgrp.getBlk();
        dft.setInr(inr);
        dft = dftMapper.selectByPrimaryKey(dft);
        if (dft == null) {
            throw new CommonServiceException("找不到DFT{" + inr + "}数据!");
        }
        dfdgrp.setBlk(dft);
        //找liacbs数据
        Date date = Dates.add(Utils.getMaxDate(), -1);
        cbsmodService.cbsGetBalance(dfdgrp.getCbs().getMax(), "DFD", inr, "MAXSUM", "AMT1", date);
        cbsmodService.cbsGetBalance(dfdgrp.getCbs().getOpn1(), "DFD", inr, "OPN", "AMT1", date);

        //找ptspta数据
        Map<String, PtsptaVo> maps = ptsptaToolComponent.getPtsptaList(inr, "DFD");
        if (maps.size() > 0) {
            maps.keySet().forEach(key -> {
                Utils.setFieldValue(dfdgrp, key.toLowerCase(), maps.get(key));
            });
        }
        return dfdgrp;
    }

    public void collectDfdCbsMap(TransactionServiceSet set, String prefix, Dfacbs cbs, String... cbsNames) {
        Map<String, Cbb> cbsMap = set.getCbsMap();
        if (cbsMap == null) {
            cbsMap = new HashMap<>();
        }
        for (String name : cbsNames) {
            Cbb cbb = Utils.getFieldValue(cbs, name);
            if (cbb != null) {
                cbsMap.put(prefix.toUpperCase() + name.toUpperCase(), cbb);
            }
        }
        set.setCbsMap(cbsMap);
    }

    public void collectDfdPtsList(TransactionServiceSet set, Dfdgrp dfdgrp, String... ptsNames) {
        if (ptsNames == null) {
            //找所有的ptspta对象
            Field[] fields = dfdgrp.getClass().getDeclaredFields();
            for (Field field : fields) {
                field.setAccessible(true);
                if (PtsptaVo.class.equals(field.getType())) {
                    PtsptaVo ptspta = Utils.getFieldValue(dfdgrp, field.getName());
                    if (ptspta != null) {
                        set.addPtspta(ptsptaToolComponent.fillPtspta(ptspta));
                    }
                }
            }
        } else {
            for (String name : ptsNames) {
                PtsptaVo ptspta = Utils.getFieldValue(dfdgrp, name);
                if (ptspta != null) {
                    set.addPtspta(ptsptaToolComponent.fillPtspta(ptspta));
                }
            }
        }
    }

    public void collectDfdPtsList(TransactionServiceSet set, FremsgVo fremsg, String... ptsNames) {
        if (ptsNames == null) {
            //找所有的ptspta对象
            Field[] fields = fremsg.getClass().getDeclaredFields();
            for (Field field : fields) {
                field.setAccessible(true);
                if (PtsptaVo.class.equals(field.getType())) {
                    PtsptaVo ptspta = Utils.getFieldValue(fremsg, field.getName());
                    if (ptspta != null) {
                        set.addPtspta(ptsptaToolComponent.fillPtspta(ptspta));
                    }
                }
            }
        } else {
            for (String name : ptsNames) {
                PtsptaVo ptspta = Utils.getFieldValue(fremsg, name);
                if (ptspta != null) {
                    set.addPtspta(ptsptaToolComponent.fillPtspta(ptspta));
                }
            }
        }
    }

}
