package com.brilliance.isc.common.api.bch.service.impl;

import com.brilliance.isc.annotation.FilterBch;
import com.brilliance.isc.bo.Atpbch;
import com.brilliance.isc.bo.Bch;
import com.brilliance.isc.common.api.bch.service.BchService;
import com.brilliance.isc.common.context.SettleContext;
import com.brilliance.isc.mda.dao.AtpbchMapper;
import com.brilliance.isc.mda.dao.BchMapper;
import com.brilliance.isc.mda.dao.UroMapper;
import com.brilliance.isc.vo.manager.BchVo;
import com.brilliance.mda.runtime.mda.util.MdaUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Service
public class BchServiceImpl implements BchService {

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

    private static final String TYPE = "BCH";

    private static final long EXPIRETIMES = 10l;

    private static final TimeUnit EXPIRETYPE = TimeUnit.MINUTES;

    public static final String ZONGHANGLEV = "0";
    public static final String ZHIHANGLEV = "2";
    public static final String QUANXIALEV1 = "A";
    public static final String QUANXIALEV2 = "B";

    @Resource
    private BchMapper bchMapper;

    @Resource
    private AtpbchMapper atpbchMapper;

    @Resource
    private UroMapper uroMapper;

    @Autowired
    private SettleContext settleContext;

    @Autowired
    @Qualifier("jacksonRedisTemplate")
    private RedisTemplate<String, Object> redisTemplate;

    // key:branch 核心机构号 value:bch 国结机构对象
    private static ThreadLocal<HashMap<String, Bch>> branchCacheThreadLocal = new ThreadLocal<>();

    // key:inr bch表主键 value:bch 国结机构对象
    private static ThreadLocal<HashMap<String, Bch>> bchInrCacheThreadLocal = new ThreadLocal<>();

    public static void setBranchCacheMap(HashMap<String, Bch> cacheMap) {
        branchCacheThreadLocal.set(cacheMap);
    }

    public static HashMap<String, Bch> getBranchCacheMap() {
        return branchCacheThreadLocal.get();
    }

    public static void removeBranchCacheMap() {
        branchCacheThreadLocal.remove();
    }

    public static void setBchInrCacheMap(HashMap<String, Bch> cacheMap) {
        bchInrCacheThreadLocal.set(cacheMap);
    }

    public static HashMap<String, Bch> getBchInrCacheMap() {
        return bchInrCacheThreadLocal.get();
    }

    public static void removeBchInrCacheMap() {
        bchInrCacheThreadLocal.remove();
    }

    // 总行
    private static final String HEAD_BRANCH_LEVEL = "0";

    // 一级全辖
    private static final String JURISDICTION_ONE_LEVEL = "A";

    // 二级全辖
    private static final String JURISDICTION_TWO_LEVELS = "B";

    // 分行
    private static final String BRANCH_LEVEL = "1";

    // 支行
    private static final String SUB_BRANCH_LEVEL = "2";

    // 经办行
    private static final String HANDLING_BRANCH = "1";

    // 收单行
    private static final String ACQUIRING_BRANCH = "6";

    // 自贸区标识
    private static final String FTA_TYPE = "X";

    @Override
    public int insert(Bch record) {
        return bchMapper.insert(record);
    }

    @Override
    public int insertSelective(Bch record) {
        return bchMapper.insertSelective(record);
    }

    @Override
    public int updateByPrimaryKeySelective(Bch record) {
        return bchMapper.updateByPrimaryKeySelective(record);
    }

    @Override
    public int updateByPrimaryKey(Bch record) {
        return bchMapper.updateByPrimaryKey(record);
    }

    @Override
    public int deleteByPrimaryKey(Bch record) {
        return bchMapper.deleteByPrimaryKey(record);
    }

    @Override
    public Bch selectByPrimaryKey(Bch record) {
        return bchMapper.selectByPrimaryKey(record);
    }

    @Override
    public List<Bch> listByUpbranch(Bch record) {
        return bchMapper.listByUpbranch(record);
    }

    @Override
    public List<Bch> listByRecord(Bch record) {
        return bchMapper.selectByRecord(record);
    }

    private List<Atpbch> orderbchs;

    @Override
    public Bch getByBranch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
        HashMap<String, Bch> branchCacheMap = getBranchCacheMap();
        if (branchCacheMap != null && branchCacheMap.containsKey(branch)) {
            logger.info("Get the response from the cache");
            Bch bch = branchCacheMap.get(branch);
            logger.info("The response is:[{}], bchlev:[{}], bchtyp:[{}]", bch.getBranch(), bch.getLev(), bch.getBchtyp());
            return bch;
        }

        logger.info("Get the response from the database");
        Bch bch = bchMapper.selectByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return null;
        }
        if (branchCacheMap == null) {
            HashMap<String, Bch> initHashMap = new HashMap<>();
            initHashMap.put(branch, bch);
            setBranchCacheMap(initHashMap);
        } else {
            branchCacheMap.put(branch, bch);
        }

        logger.info("The response is:[{}], bchlev:[{}], bchtyp:[{}]", bch.getBranch(), bch.getLev(), bch.getBchtyp());
        return bch;
    }

    @Override
    public Bch getByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return getByBranch(branch);
    }

    @Override
    public List<Bch> listAccBch(String branch) {
        return bchMapper.selectAccBchListByBranch(branch);
    }

    public List<Bch> listAccBchAndIt(String branch) {
        return bchMapper.selectAccBchListByBranchAndIt(branch);
    }

    @Override
    public List<Bch> listAccBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAccBch(branch);
    }

    @Override
    public Bch getDirectAccBch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
//        // 针对自贸区特殊处理
//        // 获取当前登录用户的所属机构，如果是自贸区，则直接返回自贸区作为记账机构
//        SessionUserVo sessionUserVo = SettleContext.getSessionUserVo();
//        if (sessionUserVo != null && StringUtils.isNotEmpty(sessionUserVo.getOwnOrgDepartmentNumber())) {
//            String ownOrgDepartmentNumber = sessionUserVo.getOwnOrgDepartmentNumber();
//            Bch ownOrgBch = getByBranch(ownOrgDepartmentNumber);
//            if (FTA_TYPE.equalsIgnoreCase(ownOrgBch.getZmqflg())
//                    && (HANDLING_BRANCH.equalsIgnoreCase(ownOrgBch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(ownOrgBch.getBchtyp()))) {
//                logger.info("The orgBch of the current login user is a FTA and a accBch, the response is:[{}] ", ownOrgBch);
//                return ownOrgBch;
//            }
//        }
        Bch bch = getByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return null;
        }
        // 自贸区
        if (StringUtils.isNotEmpty(bch.getZmqflg()) && (HANDLING_BRANCH.equalsIgnoreCase(bch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(bch.getBchtyp()))) {
            logger.info("The req bch is a FTA and a accBch, the response is itself, bchlev:[{}], bchtyp:[{}]", bch.getLev(), bch.getBchtyp());
            return bch;
        }
        // 一级、二级全辖
        int offset = 1;
        // 分行、支行
        if (HEAD_BRANCH_LEVEL.equalsIgnoreCase(bch.getLev()) || BRANCH_LEVEL.equalsIgnoreCase(bch.getLev()) || SUB_BRANCH_LEVEL.equalsIgnoreCase(bch.getLev())) {
            logger.info("The req bch is the head office or branch or sub-branch, bchlev:[{}], bchtyp:[{}]", bch.getLev(), bch.getBchtyp());
            offset = 2;
        }
        String[] paths = bch.getUpbranch().split(",");
        for (int i = paths.length - offset; i >= 0; i--) {
            Bch defaultAccBch = getDefaultAccBch(paths[i]);
            if (defaultAccBch != null) {
                logger.info("The req bch is not head office, the response is:[{}], bchlev:[{}], bchtyp:[{}]", defaultAccBch.getBranch(), bch.getLev(), bch.getBchtyp());
                return defaultAccBch;
            }
        }
        // 总行
        logger.warn("The req bch is the head office, the response is null");
        return null;
    }

    @Override
    public Bch getDirectAccBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return getDirectAccBch(branch);
    }

    @Override
    @FilterBch
    public List<Bch> listAllDirectChildSubBchByAccBch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
        Bch bch = getByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return null;
        }
        // 记账机构
        if (HANDLING_BRANCH.equalsIgnoreCase(bch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(bch.getBchtyp())) {
            logger.info("The req bch is a accBch, bchlev:[{}], bchtyp:[{}]", bch.getLev(), bch.getBchtyp());
            // 自贸区
            if (FTA_TYPE.equalsIgnoreCase(bch.getZmqflg())) {
                logger.info("The req bch is a FTA, zmqFlg:[{}]", bch.getZmqflg());
                return listAllDirectBchListByZmq(bch);
            }
            String[] splits = bch.getUpbranch().split(",");
            // 记账机构的全辖 的 直属下级 分行、支行
            List<Bch> bchList = listAllDirectChildExcludeJurisdictionBch(splits[splits.length - 2]);
            // 排除自贸区
            return bchList.stream().filter(item -> StringUtils.isEmpty(item.getZmqflg())).collect(Collectors.toList());
        }
        logger.warn("The req bch is not a accBch, the response is null");
        return null;
    }

    @Override
    public List<Bch> listAllDirectChildSubBchByAccBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllDirectChildSubBchByAccBch(branch);
    }

    @Override
    @FilterBch
    public List<Bch> listAllChildSubBchByAccBch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
        ArrayList<Bch> result = new ArrayList<>();
        Bch bch = getByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return result;
        }
        // 是记账机构
        if (HANDLING_BRANCH.equalsIgnoreCase(bch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(bch.getBchtyp())) {
            // 自贸区
            logger.info("The req bch is a accBch, bchlev:[{}], bchtyp:[{}]", bch.getLev(), bch.getBchtyp());
            if (FTA_TYPE.equalsIgnoreCase(bch.getZmqflg())) {
                logger.info("The req bch is a FTA, zmqFlg:[{}]", bch.getZmqflg());
                return listAllBchListByZmq(bch);
            }
            // 直属上级
            Bch parentBch = getDirectParentBch(bch.getBranch());
            // 所有分行、支行
            List<Bch> bchList = listAllChildExcludeJurisdictionBch(parentBch.getBranch());
            // 排除自贸区
            List<Bch> collect = bchList.stream().filter(item -> StringUtils.isEmpty(item.getZmqflg())).collect(Collectors.toList());
            for (Bch bchTemp : collect) {
                // 查看当前全辖所在下标
                String[] paths = bchTemp.getUpbranch().split(",");
                List<String> pathList = Arrays.stream(paths).collect(Collectors.toList());
                int currentIndex = pathList.indexOf(parentBch.getBranch()); // 1
                boolean hasAuthority = false;
                for (int i = paths.length - 2; i >= currentIndex + 1; i--) {
                    // 二级全辖
                    Bch defaultAccBch = getDefaultAccBch(pathList.get(i));
                    if (defaultAccBch != null) {
                        hasAuthority = true;
                        break;
                    }
                }
                if (!hasAuthority) {
                    result.add(bchTemp);
                }
            }
        }
        return result;
    }

    @Override
    public List<Bch> listAllChildSubBchByAccBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllChildSubBchByAccBch(branch);
    }

    @Override
    public Bch getDirectParentBch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
        Bch bch = getByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return null;
        }
        String[] paths = bch.getUpbranch().split(",");
        if (paths.length < 2) {
            // 返回本身（总行）
            return bch;
        }
        String path = paths[paths.length - 2];
        return getByBranch(path);
    }

    @Override
    public Bch getDirectParentBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return getDirectParentBch(branch);
    }

    @FilterBch
    @Override
    public List<Bch> listAllChildAndItselfBch(String branch) {
        return selectChildBchListByBranch(branch);
    }

    @Override
    public List<Bch> listAllChildAndItselfBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllChildAndItselfBch(branch);
    }

    @FilterBch
    @Override
    public List<Bch> listAllChildBch(String branch) {
        List<Bch> bchList = selectChildBchListByBranch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> !item.getBranch().equalsIgnoreCase(branch)).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllChildBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllChildBch(branch);
    }

    @Override
    public List<Bch> listAllChildExcludeJurisdictionBch(String branch) {
        List<Bch> bchList = listAllChildBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> (SUB_BRANCH_LEVEL.equalsIgnoreCase(item.getLev()) || BRANCH_LEVEL.equalsIgnoreCase(item.getLev()))).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllChildJurisdictionBch(String branch) {
        List<Bch> bchList = listAllChildBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> (BRANCH_LEVEL.equalsIgnoreCase(item.getLev()))).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllChildExcludeJurisdictionBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllChildExcludeJurisdictionBch(branch);
    }

    @Override
    public List<Bch> listAllChildSubBch(String branch) {
        List<Bch> bchList = listAllChildBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> SUB_BRANCH_LEVEL.equalsIgnoreCase(item.getLev())).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllChildSubBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllChildSubBch(branch);
    }

    @Override
    public List<Bch> listAllDirectChildBch(String branch) {
        ArrayList<Bch> result = new ArrayList<>();
        List<Bch> allChildBch = listAllChildBch(branch);
        if (allChildBch == null) {
            return null;
        }
        for (Bch bch : allChildBch) {
            String[] paths = bch.getUpbranch().split(",");
            String path = paths[paths.length - 2];
            if (branch.equalsIgnoreCase(path)) {
                result.add(bch);
            }
        }
        return result;
    }

    @Override
    public List<Bch> listAllDirectChildBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllDirectChildBch(branch);
    }

    @Override
    public List<Bch> listAllDirectChildJurisdictionBch(String branch) {
        List<Bch> bchList = listAllDirectChildBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> (JURISDICTION_ONE_LEVEL.equalsIgnoreCase(item.getLev()) || JURISDICTION_TWO_LEVELS.equalsIgnoreCase(item.getLev()))).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllDirectChildJurisdictionBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllDirectChildJurisdictionBch(branch);
    }

    @Override
    public List<Bch> listAllDirectChildExcludeJurisdictionBch(String branch) {
        List<Bch> bchList = listAllDirectChildBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> (BRANCH_LEVEL.equalsIgnoreCase(item.getLev()) || SUB_BRANCH_LEVEL.equalsIgnoreCase(item.getLev()))).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllDirectChildExcludeJurisdictionBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllDirectChildExcludeJurisdictionBch(branch);
    }

    @Override
    public List<Bch> listAllDirectChildSubBch(String branch) {
        List<Bch> bchList = listAllDirectChildExcludeJurisdictionBch(branch);
        if (bchList == null) {
            return null;
        }
        return bchList.stream().filter(item -> SUB_BRANCH_LEVEL.equalsIgnoreCase(item.getLev())).collect(Collectors.toList());
    }

    @Override
    public List<Bch> listAllDirectChildSubBchByBchInr(String inr) {
        String branch = getBranchByInr(inr);
        return listAllDirectChildSubBch(branch);
    }

    @Override
    public List<Bch> selectAllBchList() {
        return bchMapper.selectAllBchList();
    }

    @Override
    public List<Bch> selectAllAccBchList() {
        return bchMapper.selectAllAccBchList();
    }

    @Override
    public boolean isAccBch(String branch) {
        Bch bch = getByBranch(branch);
        return bch != null && BRANCH_LEVEL.equalsIgnoreCase(bch.getLev())
                && (HANDLING_BRANCH.equalsIgnoreCase(bch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(bch.getBchtyp()));
    }

    @Override
    public boolean isAccBchByInr(String inr) {
        String branch = getBranchByInr(inr);
        return isAccBch(branch);
    }

    @Override
    public List<Bch> listAllBch(String branch) {
        List<Bch> result = new ArrayList<>();
        Bch bch = getByBranch(branch);
        switch (bch.getLev()) {
            case HEAD_BRANCH_LEVEL:
                result = listAllChildExcludeJurisdictionBch(branch);
                break;
            case BRANCH_LEVEL:
                if (HANDLING_BRANCH.equalsIgnoreCase(bch.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(bch.getBchtyp())) {
                    result = listAllChildSubBchByAccBch(branch);
                } else {
                    result.add(bch);
                }
                break;
            case SUB_BRANCH_LEVEL:
                result.add(bch);
                break;
            case JURISDICTION_ONE_LEVEL:
            case JURISDICTION_TWO_LEVELS:
                Bch accBch = getDirectAccBch(branch);
                result = listAllChildSubBchByAccBch(accBch.getBranch());
                break;
            default:
                break;
        }
        return result;
    }

    @Override
    public List<Bch> dyncRead(Map<String, Object> dyncMap) {
        return bchMapper.dyncRead(dyncMap);
    }


    // 获取全辖的默认记账机构
    private Bch getDefaultAccBch(String branch) {
        logger.info("The request parameter branch:[{}]", branch);
        Bch bch = getByBranch(branch);
        if (bch == null) {
            logger.warn("The response is null");
            return null;
        }
        // 全辖
        if (JURISDICTION_ONE_LEVEL.equalsIgnoreCase(bch.getLev()) || JURISDICTION_TWO_LEVELS.equalsIgnoreCase(bch.getLev())) {
            // 获取全辖下的记账机构列表
            List<Bch> bchList = bchMapper.selectAccBchListByBranch(branch);
            if (bchList != null && bchList.size() > 0) {
                for (Bch tmp : bchList) {
                    String[] paths = tmp.getUpbranch().split(",");
                    String path = paths[paths.length - 2];
                    // 必须是该全辖下的（一级全辖不能拿二级全辖的记账机构） 且 排除自贸区
                    if (branch.equalsIgnoreCase(path) && StringUtils.isEmpty(tmp.getZmqflg())) {
                        logger.info("The response is:[{}]", tmp.getBranch());
                        return tmp;
                    }
                }
            }
        }
        logger.warn("There is no default accBch under the full jurisdiction");
        return null;
    }

    private String getBranchByInr(String inr) {
        logger.info("The request parameter inr:[{}]", inr);
        HashMap<String, Bch> bchInrCacheMap = getBchInrCacheMap();
        if (bchInrCacheMap != null && bchInrCacheMap.containsKey(inr)) {
            logger.info("Get the response from the cache");
            Bch bchValue = bchInrCacheMap.get(inr);
            logger.info("The response is:[{}]", bchValue.getBranch());
            return bchValue.getBranch();
        }

        logger.info("Get the response from the database");
        Bch bch = new Bch();
        bch.setInr(inr);
        Bch bchTemp = selectByPrimaryKey(bch);
        if (bchTemp == null) {
            logger.warn("The response is null character string");
            return "";
        }
        if (bchInrCacheMap == null) {
            HashMap<String, Bch> initHashMap = new HashMap<>();
            initHashMap.put(inr, bchTemp);
            setBchInrCacheMap(initHashMap);
        } else {
            bchInrCacheMap.put(inr, bchTemp);
        }

        logger.info("The response is:[{}]", bchTemp.getBranch());
        return bchTemp.getBranch();
    }

    private List<Bch> listAllDirectBchListByZmq(Bch bch) {
        // 直属上级
        Bch parentBch = getDirectParentBch(bch.getBranch());
        // 默认记账机构
        Bch accBch = getDirectAccBch(parentBch.getBranch());
        List<Bch> bchList = listAllDirectChildSubBchByAccBch(accBch.getBranch());
        /* 不再过滤掉 非自贸区的记账机构 例如：上海自贸区不过滤掉上海分行
        for (Bch item : bchList) {
            if (!(HANDLING_BRANCH.equalsIgnoreCase(item.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(item.getBchtyp()))
                    && StringUtils.isEmpty(item.getZmqflg())) {
                result.add(item);
            }
        }*/

        // 本身
        bchList.add(bch);
        return bchList;
    }

    private List<Bch> listAllBchListByZmq(Bch bch) {
        // 直属上级
        Bch parentBch = getDirectParentBch(bch.getBranch());
        // 默认记账机构
        Bch accBch = getDirectAccBch(parentBch.getBranch());
        List<Bch> bchList = listAllChildSubBchByAccBch(accBch.getBranch());
        /* 不再过滤掉 非自贸区的记账机构 例如：上海自贸区不过滤掉上海分行
        for (Bch item : bchList) {
            if (!(HANDLING_BRANCH.equalsIgnoreCase(item.getBchtyp()) || ACQUIRING_BRANCH.equalsIgnoreCase(item.getBchtyp()))
                    && StringUtils.isEmpty(item.getZmqflg())) {
                result.add(item);
            }
        }*/
        // 本身
        bchList.add(bch);
        return bchList;
    }

    @Override
    public List<String> listAllChildAndItselfBchInr(String branch) {
        return bchMapper.selectChildBchInrListByBranch(branch);
    }


    @Override
    public String getInifrmByBranchFrm(String branch, String frmtyp) {
        if (branch == null || frmtyp == null || "".equals(branch) || "".equals(frmtyp)) {
            return "";
        }

        Atpbch inAtpbch = new Atpbch();
        inAtpbch.setBranch(branch);
        inAtpbch.setFrmtyp(frmtyp);
        inAtpbch.setFlg("X");
        Atpbch outAtpbch = atpbchMapper.selectByBo(inAtpbch);
        if (outAtpbch != null && !"".equals(outAtpbch)) {
            return outAtpbch.getInifrm() == null ? "" : outAtpbch.getInifrm();
        } else {
            return "";
        }

    }

    @Override
    public String getStartFlgByBranchInifrm(String branch, String inifrm) {
        if (branch == null || inifrm == null || "".equals(branch) || "".equals(inifrm)) {
            return "2";
        }
        Atpbch inAtpbch = new Atpbch();
        inAtpbch.setBranch(branch);
        inAtpbch.setInifrm(inifrm);
        inAtpbch.setFlg("X");
        Atpbch outAtpbch = atpbchMapper.selectByBo(inAtpbch);

        if (outAtpbch != null && !"".equals(outAtpbch)) {
            if (inifrm.equals(outAtpbch.getInifrm())) {
                return "1";
            }
            return "2";
        } else {
            return "2";
        }
    }


    @Override
    public boolean isSdanfrmByBranchInifrm(String branch, String inifrm) {
        if (branch == null || inifrm == null || "".equals(branch) || "".equals(inifrm)) {
            return false;
        }
        Atpbch inAtpbch = new Atpbch();
        inAtpbch.setBranch(branch);
        inAtpbch.setInifrm(inifrm);
        inAtpbch.setNegflg("X");
        Atpbch outAtpbch = atpbchMapper.selectByBo(inAtpbch);

        if (outAtpbch != null && !"".equals(outAtpbch)) {
            if (inifrm.equals(outAtpbch.getInifrm())) {
                return true;
            }
            return false;
        } else {
            return false;
        }
    }

    public List<String> selectByUroUserId(String branch, int userId) {
        List<String> uroList = bchMapper.selectByUroUserId(userId);
        List<String> bchList = this.listAllChildAndItselfBchInr(branch);
        List<String> userList = uroList.stream().filter(bchList::contains).collect(Collectors.toList());
        return userList;
    }

    @Override
    public List<Bch> listAllByOwnExtKey(String branch) {
        List<Bch> bchList = new ArrayList<>();
        if (MdaUtils.isEmpty(branch)) {
            settleContext.simpleLoadSettleSession();
            if (SettleContext.getUserSession().getBch() != null) {
                String bckkey = SettleContext.getUserSession().getBch().getBranch();
                bchList.addAll(this.listAllChildSubBchByAccBch(bckkey));
            }
        } else {
            Bch bch = this.getByBranch(branch);
            if (!MdaUtils.isEmpty(bch)) {
                bchList.add(bch);
            }
        }
        return bchList;
    }

    private List<Bch> selectChildBchListByBranch(String branch) {
        String key = generatekey("SELECTCHILDBCHLISTBYBRANCH_" + branch);
        List<Bch> bchList = (List<Bch>) redisTemplate.opsForValue().get(key);
        if (bchList == null) {
            logger.debug("Redis中不存在key：" + key + "或者已经过期，查数据库");
            bchList = bchMapper.selectChildBchListByBranch(branch);
            redisTemplate.opsForValue().set(key, bchList, EXPIRETIMES, EXPIRETYPE);
            return bchList;

        } else {
            logger.debug("Redis中存在key：" + key + "直接返回");
            return bchList;
        }
    }

    public String generatekey(String inr) {
        return TYPE + "_" + inr;
    }

    @Override
    public List<Bch> getBchcodelist(BchVo bch) {
        List<Bch> bchList = new ArrayList<>();
        if (bch != null && !MdaUtils.isEmpty(bch.getBranch())) {
            Bch orgBch = getByBranch(bch.getBranch());
            // 获取用户当前机构之后，获取当前机构下辖经办机构列表
            // 支行调用listAllChildAndItselfBch
            if (ZHIHANGLEV.equalsIgnoreCase(orgBch.getLev())) {
                // 支行返回自己
                bchList = listAllChildAndItselfBch(orgBch.getBranch());
            } else if (ZONGHANGLEV.equalsIgnoreCase(orgBch.getLev()) || QUANXIALEV1.equalsIgnoreCase(orgBch.getLev()) || QUANXIALEV2.equalsIgnoreCase(orgBch.getLev())) {
                // 总行，全辖返回下级分支行
                bchList = listAllChildExcludeJurisdictionBch(orgBch.getBranch());
            } else {
                // 分行返回可经办机构列表
                bchList = listAllChildSubBchByAccBch(orgBch.getBranch());
            }
        }
        return bchList;
    }

    @Override
    public boolean isOrderBranch(String branch) {
        try {
            Bch bch = bchMapper.selectByBranch(branch);
            return "6".equals(bch.getBchtyp());
        } catch (Exception ex) {
            logger.info("", ex);
        }

        return false;
    }

    @Override
    public boolean isOrderBranchByFrm(String inifrm) {
        if (CollectionUtils.isEmpty(orderbchs)) {
            orderbchs = atpbchMapper.selectOrderFrm();
        }
        List<Atpbch> orders = orderbchs.stream().filter(atpbch ->
                atpbch.getInifrm().equals(inifrm)
        ).collect(Collectors.toList());
        return !CollectionUtils.isEmpty(orders);
    }

}
